Changes of Revision 10
sview.changes
Changed
x
1
2
-------------------------------------------------------------------
3
+Tue Aug 24 12:45:46 UTC 2021 - Luigi Baldoni <aloisio@gmx.com>
4
+
5
+- Update to version 20.08
6
+ * Added support for Equiangular Cubemaps (EAC).
7
+ version 20.05:
8
+ * Added Spanish translation files.
9
+ * Image Viewer - added trilinear texture filtering option
10
+ generating mip-maps.
11
+ * Image Viewer - support 1x6 cubemap layout.
12
+ * Image Viewer - panorama is now automatically enabled for
13
+ JPEG files with GPano:ProjectionType tag.
14
+ * Image Viewer - panorama is now automatically enabled for
15
+ JPEG files with 360Stereo/360Mono tags (game screenshots).
16
+ * Image Viewer - support DDS-packed cubemaps.
17
+ * Movie Player - image-based subtitles size can be now
18
+ adjusted.
19
+ * Movie Player - workaround subtitles seeking issues for
20
+ attached SRT files.
21
+ * Movie Player - fixed ASS subtitles formatting issue on files
22
+ without closure tags.
23
+ * Movie Player - added handling of image-based subtitles
24
+ encoded as stereoscopic pair (side-by-side).
25
+ * Image Viewer - fixed poor quality on saving JPEG (yuv420p)
26
+ image into PNG (rgb).
27
+ * Image Viewer - fixed displaying WebP images with alpha
28
+ channel (yuva pixel formats).
29
+ * fontconfig library is now used to retrieve paths to system
30
+ fonts.
31
+ version 19.08:
32
+ * Introduced VR180 (hemisphere) and cylindrical panorama input
33
+ support.
34
+ * Image Viewer now redirects video file to Movie Player and
35
+ vice versa.
36
+ * Added single-finger swipe gesture for opening next/previous
37
+ file in playlist.
38
+ * FFmpeg 4.1 support.
39
+ * Fixed sporadic text formatting issues.
40
+ version 17.10:
41
+ * Image Viewer - added Slideshow delay parameter to Settings.
42
+ * Movie Player - added general information about the stream
43
+ (bitrate, codec, PAR, DAR) in File Info dialog.
44
+ * Movie Player - fixed seeking to the very beginning of the
45
+ file.
46
+ * Movie Player - fixed (workaround) displaying attached image
47
+ within some mp3 files.
48
+ * Fixed text rendering artifacts when using glyphs with
49
+ kerning defined.
50
+ * Fixed compilation on glibc 2.26+.
51
+
52
+-------------------------------------------------------------------
53
Fri May 4 14:03:47 UTC 2018 - olaf@aepfle.de
54
55
- Use ffmpeg3 versions of pkgconfig(libav*)
56
sview.spec
Changed
70
1
2
#
3
# spec file for package sview
4
#
5
+# Copyright (c) 2021 Packman Team <packman@links2linux.de>
6
# Copyright (c) 2015 SUSE LINUX GmbH, Nuernberg, Germany.
7
#
8
# All modifications and additions to the file contributed by third parties
9
10
#
11
12
13
-%define src_ver 17_04
14
+%define src_ver 20_08
15
%define src_name sView
16
%define ffmpeg_includedir %(pkg-config --variable=includedir libavcodec)
17
Name: sview
18
-Version: 17.04
19
+Version: 20.08
20
Release: 0
21
Summary: Stereoscopic media player
22
-License: GPL-3.0+ and LGPL-3.0+
23
+License: GPL-3.0-or-later AND LGPL-3.0-or-later
24
Group: Productivity/Multimedia/Video/Players
25
-Url: http://www.sview.ru/en/
26
+URL: http://www.sview.ru/en/
27
Source: https://github.com/gkv311/sview/archive/%{src_ver}.tar.gz#/%{name}-%{src_ver}.tar.gz
28
BuildRequires: dos2unix
29
-BuildRequires: gcc-c++
30
BuildRequires: fdupes
31
+BuildRequires: gcc-c++
32
BuildRequires: hicolor-icon-theme
33
BuildRequires: make
34
BuildRequires: pkgconfig
35
BuildRequires: update-desktop-files
36
+BuildRequires: pkgconfig(freetype2)
37
BuildRequires: pkgconfig(gl)
38
BuildRequires: pkgconfig(gtk+-2.0)
39
-BuildRequires: pkgconfig(freetype2)
40
BuildRequires: pkgconfig(libavcodec) = 57.107.100
41
BuildRequires: pkgconfig(libavformat) = 57.83.100
42
BuildRequires: pkgconfig(libavutil) = 55.78.100
43
44
Requires: xdg-utils
45
#Recommends: mongoose
46
ExclusiveArch: %{ix86} x86_64
47
-BuildRoot: %{_tmppath}/%{name}-%{version}-build
48
49
%description
50
Stereoscopic Image Viewer and Movie Player.
51
52
-e '/^CFLAGS/s/$/\ %{optflags}/' \
53
-e '/^CXXFLAGS/s/$/\ %{optflags}/' \
54
-i Makefile
55
-# Remove %%_smp_mflags to avoid compilation errors
56
+# Remove %%{?_smp_mflags} to avoid compilation errors
57
make -j1 EXTRA_LDFLAGS="-Wl,-rpath,%{_libdir}/%{src_name}"
58
59
%install
60
61
%desktop_database_postun
62
63
%files
64
-%defattr(-,root,root)
65
-%doc LICENSE*
66
+%license LICENSE*
67
%{_bindir}/%{src_name}
68
%{_libdir}/%{src_name}/
69
%{_datadir}/applications/%{src_name}IV.desktop
70
sview-17_04.tar.gz/.gitignore -> sview-20_08.tar.gz/.gitignore
Changed
16
1
2
*.o
3
*.obj
4
+*.class
5
*.a
6
*.vcxproj.user
7
sView.Cpp.Custom.props
8
9
Doxygen/
10
distribution/repository/
11
distribution/temp/
12
+distribution/build-*
13
3rdparty/atlmfc
14
3rdparty/OCCT/inc/
15
3rdparty/OCCT/lib/
16
sview-17_04.tar.gz/.travis.yml -> sview-20_08.tar.gz/.travis.yml
Changed
29
1
2
sudo: required
3
dist: trusty
4
5
+# require Ubuntu 16.04 Xenial Xerus
6
+#dist: xenial
7
+
8
addons:
9
apt:
10
packages:
11
12
- libavformat-dev
13
- libavutil-dev
14
- libswscale-dev
15
+ homebrew:
16
+ packages:
17
+ - freetype
18
+ - ffmpeg
19
+ update: true
20
21
-before_install:
22
- - if [[ "$MY_TARGET" == "osx" ]]; then brew update; fi
23
- - if [[ "$MY_TARGET" == "osx" ]]; then brew install freetype ffmpeg; fi
24
+#before_install:
25
+# - if [[ "$MY_TARGET" == "osx" ]]; then brew update; fi
26
27
install: true
28
29
sview-17_04.tar.gz/3rdparty/FFmpeg/rebuild.sh -> sview-20_08.tar.gz/3rdparty/FFmpeg/rebuild.sh
Changed
231
1
2
3
echo "Usage: $0 [FFmpegPath] [GPL || LGPL] [DEBUG || RELEASE] [GCC_PREFIX]"
4
5
-rebuildTarget="FFmpeg"
6
-rebuildLicense="LGPL"
7
+rebuildTarget="ffmpeg.git"
8
+rebuildLicense="lgpl"
9
rebuildDebug="false"
10
rebuildAndroid="false"
11
compilerPrefix=""
12
androidTarget=""
13
+androidAbi="armeabi-v7a"
14
androidNdkRoot="$HOME/develop/android-ndk-r12b"
15
aSystem=`uname -s`
16
aPwdBack=$PWD
17
18
for i in $*
19
do
20
if [ "$i" == "gpl" ] || [ "$i" == "GPL" ]; then
21
- rebuildLicense="GPL"
22
+ rebuildLicense="gpl"
23
elif [ "$i" == "lgpl" ] || [ "$i" == "LGPL" ]; then
24
- rebuildLicense="LGPL"
25
+ rebuildLicense="lgpl"
26
elif [ "$i" == "android" ]; then
27
rebuildAndroid="true"
28
elif [ "$i" == "debug" ] || [ "$i" == "DEBUG" ]; then
29
30
if [ "$rebuildAndroid" == "true" ]; then
31
if [ "$androidTarget" == "arm64" ]; then
32
aPrefixShort="aarch64-linux-android"
33
+ androidAbi="arm64-v8a"
34
else
35
aPrefixShort="arm-linux-androideabi"
36
+ androidAbi="armeabi-v7a"
37
fi
38
39
compilerPrefix="${androidNdkRoot}/toolchains/${aPrefixShort}-4.8/prebuilt/linux-x86_64/bin/${aPrefixShort}-"
40
41
echo " Start building FFmpeg $rebuildLicense from $rebuildTarget"
42
cd $rebuildTarget
43
44
-# releases extract the version number from the VERSION file
45
-ffmpegVersion=$(cat VERSION 2> /dev/null)
46
+# releases extract the version number from the RELEASE file
47
+ffmpegVersion=$(cat RELEASE 2> /dev/null)
48
ffmpegRevision=$(git log -1 --pretty=format:%h 2> /dev/null)
49
ffmpegDate=$(git show -s --format="%ci" 2> /dev/null)
50
ffmpegDate=${ffmpegDate:0:10}
51
-test $ffmpegRevision && ffmpegRevision=git-$ffmpegRevision
52
+test $ffmpegRevision && ffmpegRevision=git-$ffmpegDate-$ffmpegRevision
53
test $ffmpegVersion || ffmpegVersion=$ffmpegRevision
54
55
# remove slashes
56
rebuildTarget="${rebuildTarget//\//}"
57
-SOURCES_NAME="FFmpeg-$ffmpegDate-$ffmpegVersion"
58
-OUTPUT_NAME="$SOURCES_NAME-$gccMachine-$gccVersion-$rebuildLicense"
59
+SOURCES_NAME="ffmpeg-$ffmpegVersion"
60
+#OUTPUT_NAME="$SOURCES_NAME-$gccMachine-$gccVersion-$rebuildLicense"
61
+OUTPUT_NAME="$SOURCES_NAME-$gccMachine-$rebuildLicense"
62
SOURCES_NAME="$SOURCES_NAME-src"
63
if [ "$rebuildDebug" == "true" ]; then
64
OUTPUT_NAME="$OUTPUT_NAME-debug"
65
66
OUTPUT_FOLDER_LIB="$OUTPUT_FOLDER/Frameworks"
67
fi
68
if [ "$androidTarget" == "arm64" ]; then
69
- OUTPUT_FOLDER_LIB="$OUTPUT_FOLDER/libs/arm64-v8a"
70
+ OUTPUT_FOLDER_LIB="$OUTPUT_FOLDER/libs/$androidAbi"
71
elif [ "$androidTarget" == "arm" ]; then
72
- OUTPUT_FOLDER_LIB="$OUTPUT_FOLDER/libs/armeabi-v7a"
73
+ OUTPUT_FOLDER_LIB="$OUTPUT_FOLDER/libs/$androidAbi"
74
fi
75
76
rm -f -r $OUTPUT_FOLDER
77
78
mkdir -p $OUTPUT_FOLDER_INC/libswscale
79
mkdir -p $OUTPUT_FOLDER_INC/libswresample
80
81
+# include some information about FFmpeg into archive
82
+echo \<pre\>> $OUTPUT_FOLDER/VERSION.html
83
+git status >> $OUTPUT_FOLDER/VERSION.html
84
+git log -n 100 >> $OUTPUT_FOLDER/VERSION.html
85
+echo \</pre\>>> $OUTPUT_FOLDER/VERSION.html
86
+
87
echo " make distclean"
88
make distclean &>/dev/null
89
90
91
then
92
echo "Sources archive '$SOURCES_NAME.7z' already exists"
93
else
94
+
95
+ if [ ! -f ../exclude.lst ]; then
96
+ echo -e ".svn\n.git\n" > ../exclude.lst
97
+ fi
98
7za a -t7z -m0=lzma -mx=9 -mfb=64 -md=32m -ms=on ../$SOURCES_NAME.7z ../$rebuildTarget '-xr@../exclude.lst'
99
fi
100
fi
101
102
+# --extra-cflags parameters
103
+anExtraCFlags=
104
+
105
#--enable-memalign-hack
106
configArguments="\
107
--extra-version=sView.ru \
108
109
--enable-avfilter \
110
--enable-hardcoded-tables \
111
--enable-pthreads \
112
- --disable-libopenjpeg \
113
--disable-doc \
114
--enable-runtime-cpudetect"
115
116
117
configArguments="$configArguments --enable-vda --libdir=@executable_path/../Frameworks"
118
fi
119
120
+export PKG_CONFIG_LIBDIR=
121
+
122
#if [ "$gccMachine" != "$GCC_MACHINE_LINUX_64" ]; then
123
if [ "$gccMachine" == "$GCC_MACHINE_MINGW_32" ] || [ "$gccMachine" == "$GCC_MACHINE_MINGW_32_1" ] \
124
|| [ "$gccMachine" == "$GCC_MACHINE_MINGW_64" ] || [ "$gccMachine" == "$GCC_MACHINE_MINGW_64_1" ]; then
125
126
# you should use with --enable-pthreads instead to enable full multithreading support!
127
#configArguments="$configArguments --enable-w32threads"
128
configArguments="$configArguments --disable-w32threads"
129
- if [ "$rebuildLicense" == "GPL" ]; then
130
+ if [ "$rebuildLicense" == "gpl" ]; then
131
configArguments="$configArguments --enable-avisynth"
132
fi
133
134
+ aMingwRoot=${compilerPrefix::-1}
135
+ export PKG_CONFIG_LIBDIR=/usr/$aMingwRoot/share/pkgconfig
136
+
137
configArguments="$configArguments --enable-libopenjpeg"
138
139
# avoid dynamic linkage with libgcc_s_sjlj-1.dll
140
configArguments="$configArguments --extra-ldflags=-static-libgcc"
141
+else
142
+ configArguments="$configArguments --disable-libopenjpeg"
143
fi
144
145
# cross-compiling options
146
147
targetFlags="--cross-prefix=$compilerPrefix --arch=x86_32"
148
configArguments="$configArguments --enable-cross-compile --target-os=mingw32 $targetFlags"
149
elif [ "$gccMachine" == "$GCC_MACHINE_MINGW_64" ] || [ "$gccMachine" == "$GCC_MACHINE_MINGW_64_1" ]; then
150
+ anExtraCFlags="$anExtraCFlags -Dstrtod=__strtod"
151
targetFlags="--cross-prefix=$compilerPrefix --arch=x86_64 --extra-cflags=-Dstrtod=__strtod"
152
configArguments="$configArguments --enable-cross-compile --target-os=mingw32 $targetFlags"
153
elif [ "$rebuildAndroid" == "true" ]; then
154
+ anAndArch=arm
155
+ anAndSysRoot=${androidNdkRoot}/platforms/android-15/arch-arm
156
if [ "$androidTarget" == "arm64" ]; then
157
- targetFlags="--cross-prefix=$compilerPrefix --sysroot=${androidNdkRoot}/platforms/android-21/arch-arm64 --arch=aarch64"
158
- else
159
- targetFlags="--cross-prefix=$compilerPrefix --sysroot=${androidNdkRoot}/platforms/android-15/arch-arm --arch=arm"
160
+ anAndArch=aarch64
161
+ anAndSysRoot=${androidNdkRoot}/platforms/android-21/arch-arm64
162
fi
163
+ configArguments="$configArguments --enable-cross-compile --target-os=android --cross-prefix=$compilerPrefix --sysroot=${anAndSysRoot} --arch=${anAndArch}"
164
+ #if [ -x "${androidNdkRoot}/sysroot" ]; then
165
+ #configArguments="$configArguments --sysinclude=${androidNdkRoot}/sysroot/usr/include"
166
+ #fi
167
168
- configArguments="$configArguments --enable-cross-compile --target-os=android $targetFlags"
169
- #configArguments="$configArguments --extra-cflags='-fno-builtin-sin -fno-builtin-sinf'"
170
+ if [ "$androidTarget" == "arm64" ]; then
171
+ anExtraCFlags="$anExtraCFlags -march=armv8-a"
172
+ else
173
+ anExtraCFlags="$anExtraCFlags -march=armv7-a -mfloat-abi=softfp -fno-builtin-sin -fno-builtin-sinf"
174
+ fi
175
176
configArguments="$configArguments --enable-jni --enable-mediacodec"
177
+
178
+ configArguments="$configArguments --enable-mbedtls --extra-ldflags=-L$aPwdBack/mbedtls-2.16.2-android/libs/$androidAbi"
179
+ anExtraCFlags="$anExtraCFlags -I$aPwdBack/mbedtls-2.16.2-android/include"
180
fi
181
182
# More options
183
184
# enable (L)GPL version 3
185
configArguments="$configArguments --enable-version3"
186
187
-if [ "$rebuildLicense" == "GPL" ]; then
188
+if [ "$rebuildLicense" == "gpl" ]; then
189
configArguments="$configArguments --enable-gpl"
190
# enable libx264 encoder (should be compiled and installed!)
191
#configArguments="$configArguments --enable-libx264"
192
193
set -o pipefail
194
195
aNbJobs="$(getconf _NPROCESSORS_ONLN)"
196
+"$compilerPrefix"gcc --version > $OUTPUT_FOLDER/gccInfo-$gccMachine-$rebuildLicense.log
197
+
198
+# --extra-cflags should be passed as single dedicated argument
199
+anExtraCFlags="--extra-cflags=${anExtraCFlags}"
200
201
echo
202
-echo " ./configure $configArguments"
203
+echo " ./configure $configArguments $anExtraCFlags"
204
echo
205
if [ "$rebuildAndroid" == "true" ]; then
206
- if [ "$androidTarget" == "arm64" ]; then
207
- ./configure $configArguments --disable-symver --extra-cflags='-march=armv8-a' 2>&1 | tee $OUTPUT_FOLDER/config.log
208
- else
209
- ./configure $configArguments --disable-symver --extra-cflags='-march=armv7-a -mfloat-abi=softfp -fno-builtin-sin -fno-builtin-sinf' 2>&1 | tee $OUTPUT_FOLDER/config.log
210
- fi
211
+ ./configure $configArguments --disable-symver "$anExtraCFlags" 2>&1 | tee $OUTPUT_FOLDER/config-$gccMachine-$rebuildLicense.log
212
else
213
- ./configure $configArguments 2>&1 | tee -a $OUTPUT_FOLDER/config.log
214
+ ./configure $configArguments 2>&1 | tee -a $OUTPUT_FOLDER/config-$gccMachine-$rebuildLicense.log
215
fi
216
aResult=$?; if [[ $aResult != 0 ]]; then exit $aResult; fi
217
218
-make -j $aNbJobs 2>&1 | tee -a $OUTPUT_FOLDER/make.log
219
+make -j $aNbJobs 2>&1 | tee -a $OUTPUT_FOLDER/make-$gccMachine-$rebuildLicense.log
220
aResult=$?; if [[ $aResult != 0 ]]; then exit $aResult; fi
221
222
# Now copy result files
223
echo
224
echo " Now copy result files into $OUTPUT_FOLDER"
225
226
-"$compilerPrefix"gcc --version > $OUTPUT_FOLDER/gccInfo.log
227
-
228
if [ -f libavcodec/avcodec.dll ]; then
229
cp -f libavcodec/*.dll $OUTPUT_FOLDER_BIN
230
cp -f libavcodec/*.lib $OUTPUT_FOLDER_LIB &>/dev/null
231
sview-17_04.tar.gz/3rdparty/include/mongoose.c -> sview-20_08.tar.gz/3rdparty/include/mongoose.c
Changed
12
1
2
#ifndef _CRT_SECURE_NO_WARNINGS
3
#define _CRT_SECURE_NO_WARNINGS
4
#endif
5
+ #ifndef _WINSOCK_DEPRECATED_NO_WARNINGS
6
+ // Warning C4996 'inet_ntoa': Use inet_ntop() or InetNtop() instead
7
+ #define _WINSOCK_DEPRECATED_NO_WARNINGS
8
+ #endif
9
#else
10
#ifdef __linux__
11
#define _XOPEN_SOURCE 600 // For flockfile() on Linux
12
sview-20_08.tar.gz/3rdparty/mbedtls
Added
2
1
+(directory)
2
sview-20_08.tar.gz/3rdparty/mbedtls/sview_mbedtls_build_android.bat
Added
94
1
2
+@echo OFF
3
+
4
+rem Auxiliary script for semi-automated building of mbedtls (https://tls.mbed.org/) for Android platform.
5
+rem Script should be placed into root of mbedtls repository, edited with paths
6
+rem to CMake, 3rd-parties, Android NDK and MinGW64 make tool.
7
+
8
+rem CMake toolchain definition should be cloned from the following git repository:
9
+rem https://github.com/taka-no-me/android-cmake
10
+
11
+rem CMake can be downloaded from official site:
12
+rem https://cmake.org/download/
13
+
14
+rem Android NDK can be downloaded from offical site:
15
+rem https://developer.android.com/ndk/downloads
16
+
17
+rem x86 build is broken on old gcc due to https://github.com/ARMmbed/mbedtls/issues/1910
18
+rem include/mbedtls/bn_mul.h
19
+rem -#if defined(__i386__) && defined(__OPTIMIZE__) && !defined(__ANDROID__)
20
+rem +#if defined(__i386__) && defined(__OPTIMIZE__) && !defined(__ANDROID__)
21
+rem
22
+rem #define MULADDC_INIT
23
+
24
+set "anMbedTlsSrc=%~dp0"
25
+set aNbJobs=%NUMBER_OF_PROCESSORS%
26
+
27
+call c:\develop\MinGW\TDM-GCC-64\mingwvars.bat
28
+set "PATH=c:\develop\CMake\bin;%PATH%"
29
+set "anNdkPath=c:/develop/android/android-ndk-r12"
30
+set "aToolchain=c:/develop/android-cmake/android.toolchain.cmake"
31
+
32
+set "anInstDir=%~dp0work/mbedtls-android"
33
+if exist "%anInstDir%" ( rmdir /S /Q "%anInstDir%" )
34
+
35
+call :cmakeGenerate "15" "armeabi-v7a"
36
+call :cmakeGenerate "21" "arm64-v8a"
37
+call :cmakeGenerate "15" "x86"
38
+
39
+pause
40
+
41
+goto :eof
42
+
43
+:cmakeGenerate
44
+set "anApi=%1"
45
+set "anAbi=%2"
46
+set "aPlatformAndCompiler=android-%anAbi%-gcc"
47
+set "aWorkDir=work\%aPlatformAndCompiler%-make"
48
+set "aLogFile=%~dp0build-%anAbi%.log"
49
+if not exist "%aWorkDir%" ( mkdir "%aWorkDir%" )
50
+if exist "%aLogFile%" ( del "%aLogFile%" )
51
+
52
+pushd "%aWorkDir%"
53
+
54
+echo Configuring mbedtls for Android %anAbi% (API level %anApi%)...
55
+cmake -G "MinGW Makefiles" ^
56
+ -D CMAKE_TOOLCHAIN_FILE:FILEPATH="%aToolchain%" ^
57
+ -D ANDROID_NDK:FILEPATH="%anNdkPath%" ^
58
+ -D CMAKE_BUILD_TYPE:STRING="Release" ^
59
+ -D ANDROID_ABI:STRING="%anAbi%" ^
60
+ -D ANDROID_NATIVE_API_LEVEL:STRING="%anApi%" ^
61
+ -D ANDROID_STL:STRING="gnustl_shared" ^
62
+ -D CMAKE_INSTALL_PREFIX:PATH="%anInstDir%" ^
63
+ -D LIBRARY_OUTPUT_PATH:PATH="%anInstDir%/libs/%anAbi%" ^
64
+ -D USE_SHARED_MBEDTLS_LIBRARY:BOOL="OFF" ^
65
+ -D USE_STATIC_MBEDTLS_LIBRARY:BOOL="ON" ^
66
+ -D ENABLE_TESTING:BOOL="OFF" ^
67
+ -D ENABLE_PROGRAMS:BOOL="OFF" ^
68
+ "%anMbedTlsSrc%"
69
+
70
+if errorlevel 1 (
71
+ popd
72
+ pause
73
+ exit /B
74
+ goto :eof
75
+)
76
+
77
+mingw32-make clean
78
+
79
+echo Building mbedtls...
80
+mingw32-make -j %aNbJobs% 2>> %aLogFile%
81
+type %aLogFile%
82
+if errorlevel 1 (
83
+ popd
84
+ pause
85
+ exit /B
86
+ goto :eof
87
+)
88
+echo Installing mbedtls into %~dp0work/%aPlatformAndCompiler%...
89
+mingw32-make install 2>> %aLogFile%
90
+if exist "%anInstDir%/lib" ( rmdir /S /Q "%anInstDir%/lib" )
91
+
92
+popd
93
+goto :eof
94
sview-17_04.tar.gz/Makefile -> sview-20_08.tar.gz/Makefile
Changed
518
1
2
3
WORKDIR = $(shell pwd)
4
SRCDIR = $(WORKDIR)
5
+JAVA_HOME = /usr
6
+APP_PREFIX = /usr
7
8
$(info SRCDIR=$(SRCDIR))
9
10
11
.mm.o:
12
$(CXX) -c $(CXXFLAGS) $< -o $@
13
14
+# Compile java files.
15
+# javac takes output folder, not file, and actually sometimes generates multiple files from single .java input.
16
+# To fool make (avoid recompiling on each build) - copy result .class file to source folder;
17
+# this, however, might lead to incomplete build on .java change without make clean.
18
+.SUFFIXES: .class .java
19
+.java.class:
20
+ $(JAVA_HOME)/bin/javac -source 1.7 -target 1.7 -d $(BUILD_ROOT)/java/classes -classpath $(ANDROID_PLATFORM) -sourcepath $(SRCDIR)/sview/src:$(BUILD_ROOT)/java/gen $<
21
+ cp -f $(BUILD_ROOT)/java/classes/com/sview/$(@F) $@
22
+
23
TARGET_OS = linux
24
+TARGET_ARCH2 =
25
26
#ANDROID_NDK = $(HOME)/develop/android-ndk-r12b
27
ifeq ($(OS),Windows_NT)
28
29
endif
30
ifeq ($(UNAME_S),Darwin)
31
TARGET_OS = osx
32
+TARGET_OS_VERSION = 10.10
33
endif
34
endif
35
36
37
BUILD_ROOT = $(BUILD_ROOT_BUNDLE)/Contents/MacOS
38
endif
39
40
+ST_DEBUG = 0
41
FFMPEG_ROOT =
42
FREETYPE_ROOT =
43
OPENAL_ROOT =
44
LIBCONFIG_ROOT =
45
LIBSUBFOLDER = lib
46
LIBSUFFIX = so
47
+ANDROID_BUILD_TOOLS = $(ANDROID_HOME)/build-tools/26.0.3
48
+ANDROID_PLATFORM = $(ANDROID_HOME)/platforms/android-26/android.jar
49
+ANDROID_KEYSTORE = $(BUILD_ROOT)/sview_debug.key
50
+ANDROID_KEYSTORE_PASSWORD = sview_store_pswd
51
+ANDROID_KEY = "sview android key"
52
+ANDROID_KEY_PASSWORD = sview_pswd
53
54
# function defining library install_name to @executable_path on OS X
55
libinstname =
56
57
LIB_CONFIG =
58
LIB_ANDROID =
59
LIB_IOKIT =
60
+LIB_COREVIDEO =
61
LIB_OPENAL = -lopenal
62
LIB_OUTPUTS = -lStOutAnaglyph -lStOutDual -lStOutInterlace -lStOutPageFlip -lStOutIZ3D -lStOutDistorted
63
TOOLCHAIN =
64
65
LIB_PTHREAD = -lobjc
66
LIB_GLX = -framework OpenGL -framework Appkit
67
LIB_IOKIT = -framework IOKit
68
-LIB_OPENAL = -framework OpenAL
69
+LIB_COREVIDEO = -framework CoreVideo
70
+ifeq ($(OPENAL_ROOT),)
71
+ LIB_OPENAL = -framework OpenAL
72
+endif
73
endif
74
75
# Android libraries
76
77
LDSTRIP = -s
78
LDZDEF = -z defs
79
EXTRA_CFLAGS =
80
-EXTRA_CXXFLAGS =
81
+EXTRA_CXXFLAGS = -DAPP_PREFIX="\"$(APP_PREFIX)\""
82
EXTRA_LDFLAGS =
83
ifeq ($(TARGET_OS),osx)
84
LDZDEF =
85
endif
86
87
+CCVERSION := $(shell $(CC) -dumpversion)
88
+CCMACHINE := $(shell $(CC) -dumpmachine)
89
+
90
+ifneq (,$(findstring i586,$(CCMACHINE)))
91
+TARGET_ARCH2 = x86
92
+else ifneq (,$(findstring i686,$(CCMACHINE)))
93
+TARGET_ARCH2 = x86
94
+else ifneq (,$(findstring x86,$(CCMACHINE)))
95
+TARGET_ARCH2 = x86
96
+else ifneq (,$(findstring mingw,$(CCMACHINE)))
97
+TARGET_ARCH2 = x86
98
+endif
99
+
100
# to activate debug build
101
+ifneq ($(ST_DEBUG),0)
102
+EXTRA_CXXFLAGS = -DST_DEBUG
103
+LDSTRIP =
104
+STRIPFLAGS = --info
105
+endif
106
#EXTRA_CXXFLAGS = -DST_DEBUG_LOG_TO_FILE=\"/sdcard/Android/data/com.sview/files/sview.log\" -DST_DEBUG
107
#EXTRA_CXXFLAGS += -DST_DEBUG_GL
108
#EXTRA_CXXFLAGS += -DST_DEBUG_FFMPEG_VERBOSE
109
#EXTRA_CXXFLAGS += -DST_DEBUG_SYSLOG
110
#EXTRA_CXXFLAGS += -DST_DEBUG_THREADID
111
-#LDSTRIP =
112
-#STRIPFLAGS = --info
113
114
ifdef ANDROID_NDK
115
LIBSUBFOLDER = libs/$(ANDROID_EABI)
116
EXTRA_CFLAGS += $(ANDROID_SYSROOT) $(ANDROID_MARCH)
117
EXTRA_CXXFLAGS += $(ANDROID_SYSROOT) $(ANDROID_MARCH)
118
-EXTRA_CXXFLAGS += -I$(ANDROID_NDK)/sources/cxx-stl/gnu-libstdc++/4.9/include -I$(ANDROID_NDK)/sources/cxx-stl/gnu-libstdc++/4.9/libs/$(ANDROID_EABI)/include -DST_HAVE_EGL -DST_NO_UPDATES_CHECK
119
+EXTRA_CXXFLAGS += -I$(ANDROID_NDK)/sources/cxx-stl/gnu-libstdc++/4.9/include -I$(ANDROID_NDK)/sources/cxx-stl/gnu-libstdc++/4.9/libs/$(ANDROID_EABI)/include -DST_HAVE_EGL
120
EXTRA_LDFLAGS += $(ANDROID_SYSROOT) -L$(ANDROID_NDK)/sources/cxx-stl/gnu-libstdc++/4.9/libs/$(ANDROID_EABI) -lstdc++ -lgnustl_shared
121
-else
122
+else ifeq ($(TARGET_ARCH2),x86)
123
+# necessary for 32-bit x86 builds, where MMX and SSE are not enabled by default
124
EXTRA_CFLAGS += -mmmx -msse
125
EXTRA_CXXFLAGS += -mmmx -msse
126
endif
127
128
# todo
129
LDSTRIP =
130
131
+# minimal supported version of macOS:
132
+# - CMake: CMAKE_OSX_DEPLOYMENT
133
+# - qmake: QMAKE_MACOSX_DEPLOYMENT_TARGET = $(TARGET_OS_VERSION)
134
+# - environment variable: export MACOSX_DEPLOYMENT_TARGET=$(TARGET_OS_VERSION)
135
+EXTRA_CFLAGS += -mmacosx-version-min=$(TARGET_OS_VERSION)
136
+EXTRA_CXXFLAGS += -mmacosx-version-min=$(TARGET_OS_VERSION)
137
+
138
# workaround homebrew
139
HAS_PKGCONF := $(shell command -v pkg-config 2> /dev/null)
140
ifdef HAS_PKGCONF
141
142
143
ifeq ($(TARGET_OS),linux)
144
EXTRA_CXXFLAGS += `pkg-config gtk+-2.0 --cflags`
145
+# notification about updates available on sview.ru
146
+#EXTRA_CXXFLAGS += -DST_UPDATES_CHECK
147
+endif
148
+
149
+# optionally fail on any compiler warning except #warning and deprecations
150
+WERROR_LEVEL = 0
151
+ifeq ($(WERROR_LEVEL),1)
152
+EXTRA_CXXFLAGS += -Werror -Wno-error=cpp -Wno-error=deprecated-declarations
153
endif
154
155
INC = -I$(SRCDIR)/3rdparty/include -I$(SRCDIR)/include
156
CFLAGS = -fPIC $(HAVE_MONGOOSE) $(INC) $(EXTRA_CFLAGS)
157
+ifneq ($(ST_DEBUG),0)
158
+CXXFLAGS = -g -std=c++0x -Wall -fPIC $(HAVE_MONGOOSE) $(INC) $(EXTRA_CXXFLAGS)
159
+else
160
CXXFLAGS = -O3 -std=c++0x -Wall -fPIC $(HAVE_MONGOOSE) $(INC) $(EXTRA_CXXFLAGS)
161
+endif
162
LIBDIR = -L$(BUILD_ROOT)
163
LIB =
164
LDFLAGS = $(LDSTRIP) $(LDZDEF) $(EXTRA_LDFLAGS)
165
166
sViewAndroidCad := libsviewcad.$(LIBSUFFIX)
167
sView := sView
168
sViewAndroid := libsview.$(LIBSUFFIX)
169
-
170
-aDestAndroid := sview
171
-
172
-all: pre_all $(aStShared) $(aStGLWidgets) $(aStCore) $(aStOutAnaglyph) $(aStOutDual) $(aStOutInterlace) $(aStOutPageFlip) $(aStOutIZ3D) $(aStOutDistorted) $(aStImageViewer) $(aStMoviePlayer) $(aStDiagnostics) $(sView)
173
-android_cad: aDestAndroid = StCADViewer
174
-android_cad: pre_all $(aStShared) $(aStGLWidgets) $(aStCore) $(aStOutAnaglyph) $(aStOutInterlace) $(aStOutDistorted) $(aStImageViewer) $(aStMoviePlayer) $(sViewAndroidCad) install_android install_android_cad_libs
175
-android: pre_all $(aStShared) $(aStGLWidgets) $(aStCore) $(aStOutAnaglyph) $(aStOutInterlace) $(aStOutDistorted) $(aStImageViewer) $(aStMoviePlayer) $(sViewAndroid) install_android install_android_libs
176
+sViewApk := $(SRCDIR)/build/sView.apk
177
+sViewApkSigned := $(SRCDIR)/build/sView.signed.apk.tmp
178
+sViewApkUnsigned:= $(SRCDIR)/build/sView.unsigned.apk.tmp
179
+aDestAndroid := build/apk-tmp
180
+sViewDex := $(aDestAndroid)/classes.dex
181
+
182
+all: shared $(aStDiagnostics) $(sView)
183
+android_cad: pre_all_android shared $(sViewAndroidCad) $(sViewApk) install_android install_android_cad_libs
184
+android: pre_all_android shared $(sViewAndroid) $(sViewApk) install_android install_android_libs
185
+shared: pre_all $(aStShared) $(aStGLWidgets) $(aStCore) outputs_all $(aStImageViewer) $(aStMoviePlayer)
186
clean: clean_StShared clean_StGLWidgets clean_StCore clean_sView clean_StOutAnaglyph clean_StOutDual clean_StOutInterlace clean_StOutPageFlip clean_StOutIZ3D clean_StOutDistorted clean_StImageViewer clean_StMoviePlayer clean_StDiagnostics clean_StCADViewer clean_sViewAndroid
187
distclean: clean
188
189
190
endif
191
192
install:
193
- mkdir -p $(DESTDIR)/usr/bin
194
- mkdir -p $(DESTDIR)/usr/$(USR_LIB)/sView
195
- mkdir -p $(DESTDIR)/usr/$(USR_LIB)/firefox/plugins
196
- mkdir -p $(DESTDIR)/usr/$(USR_LIB)/mozilla/plugins
197
- mkdir -p $(DESTDIR)/usr/share
198
- mkdir -p $(DESTDIR)/usr/share/sView/info
199
- mkdir -p $(DESTDIR)/usr/share/sView/lang
200
- mkdir -p $(DESTDIR)/usr/share/sView/shaders
201
- mkdir -p $(DESTDIR)/usr/share/sView/textures
202
- mkdir -p $(DESTDIR)/usr/share/sView/web
203
- cp -f -r share/* $(DESTDIR)/usr/share/
204
- cp -f -r $(BUILD_ROOT)/lang/* $(DESTDIR)/usr/share/sView/lang/
205
- cp -f -r $(BUILD_ROOT)/shaders/* $(DESTDIR)/usr/share/sView/shaders/
206
- cp -f -r $(BUILD_ROOT)/textures/* $(DESTDIR)/usr/share/sView/textures/
207
- cp -f -r $(BUILD_ROOT)/web/* $(DESTDIR)/usr/share/sView/web/
208
- cp -f license-gpl-3.0.txt $(DESTDIR)/usr/share/sView/info/license.txt
209
- cp -f -r $(BUILD_ROOT)/*.$(LIBSUFFIX) $(DESTDIR)/usr/$(USR_LIB)/
210
- cp -f $(BUILD_ROOT)/sView $(DESTDIR)/usr/$(USR_LIB)/sView/sView
211
- ln --force --symbolic ../$(USR_LIB)/sView/sView $(DESTDIR)/usr/bin/sView
212
- ln --force --symbolic ../../share/sView/demo/demo.jps $(DESTDIR)/usr/$(USR_LIB)/sView/demo.jps
213
- rm -f $(DESTDIR)/usr/$(USR_LIB)/sView/*.a
214
+ mkdir -p $(DESTDIR)/$(APP_PREFIX)/bin
215
+ mkdir -p $(DESTDIR)/$(APP_PREFIX)/$(USR_LIB)/sView
216
+ mkdir -p $(DESTDIR)/$(APP_PREFIX)/$(USR_LIB)/firefox/plugins
217
+ mkdir -p $(DESTDIR)/$(APP_PREFIX)/$(USR_LIB)/mozilla/plugins
218
+ mkdir -p $(DESTDIR)/$(APP_PREFIX)/share
219
+ mkdir -p $(DESTDIR)/$(APP_PREFIX)/share/sView/info
220
+ mkdir -p $(DESTDIR)/$(APP_PREFIX)/share/sView/lang
221
+ mkdir -p $(DESTDIR)/$(APP_PREFIX)/share/sView/shaders
222
+ mkdir -p $(DESTDIR)/$(APP_PREFIX)/share/sView/textures
223
+ mkdir -p $(DESTDIR)/$(APP_PREFIX)/share/sView/web
224
+ cp -f -r share/* $(DESTDIR)/$(APP_PREFIX)/share/
225
+ cp -f -r $(BUILD_ROOT)/lang/* $(DESTDIR)/$(APP_PREFIX)/share/sView/lang/
226
+ cp -f -r $(BUILD_ROOT)/shaders/* $(DESTDIR)/$(APP_PREFIX)/share/sView/shaders/
227
+ cp -f -r $(BUILD_ROOT)/textures/* $(DESTDIR)/$(APP_PREFIX)/share/sView/textures/
228
+ cp -f -r $(BUILD_ROOT)/web/* $(DESTDIR)/$(APP_PREFIX)/share/sView/web/
229
+ cp -f license-gpl-3.0.txt $(DESTDIR)/$(APP_PREFIX)/share/sView/info/license.txt
230
+ cp -f -r $(BUILD_ROOT)/*.$(LIBSUFFIX) $(DESTDIR)/$(APP_PREFIX)/$(USR_LIB)/
231
+ cp -f $(BUILD_ROOT)/sView $(DESTDIR)/$(APP_PREFIX)/$(USR_LIB)/sView/sView
232
+ ln --force --symbolic ../$(USR_LIB)/sView/sView $(DESTDIR)/$(APP_PREFIX)/bin/sView
233
+ ln --force --symbolic ../../share/sView/demo/demo.jps $(DESTDIR)/$(APP_PREFIX)/$(USR_LIB)/sView/demo.jps
234
+ rm -f $(DESTDIR)/$(APP_PREFIX)/$(USR_LIB)/sView/*.a
235
236
install_android:
237
mkdir -p $(aDestAndroid)/assets/info
238
mkdir -p $(aDestAndroid)/assets/lang/German
239
mkdir -p $(aDestAndroid)/assets/lang/French
240
mkdir -p $(aDestAndroid)/assets/lang/English
241
+ mkdir -p $(aDestAndroid)/assets/lang/Spanish
242
mkdir -p $(aDestAndroid)/assets/lang/Russian
243
mkdir -p $(aDestAndroid)/assets/lang/Czech
244
mkdir -p $(aDestAndroid)/assets/lang/ChineseS
245
246
cp -f -r $(BUILD_ROOT)/lang/Deutsch/* $(aDestAndroid)/assets/lang/German/
247
cp -f -r $(BUILD_ROOT)/lang/français/* $(aDestAndroid)/assets/lang/French/
248
cp -f -r $(BUILD_ROOT)/lang/English/* $(aDestAndroid)/assets/lang/English/
249
+ cp -f -r $(BUILD_ROOT)/lang/Español/* $(aDestAndroid)/assets/lang/Spanish/
250
cp -f -r $(BUILD_ROOT)/lang/русский/* $(aDestAndroid)/assets/lang/Russian/
251
cp -f -r $(BUILD_ROOT)/lang/Czech/* $(aDestAndroid)/assets/lang/Czech/
252
cp -f -r $(BUILD_ROOT)/lang/ChineseS/* $(aDestAndroid)/assets/lang/ChineseS/
253
254
cp -f -r $(BUILD_ROOT)/shaders/* $(aDestAndroid)/assets/shaders/
255
cp -f -r $(BUILD_ROOT)/textures/* $(aDestAndroid)/assets/textures/
256
cp -f license-gpl-3.0.txt $(aDestAndroid)/assets/info/license.txt
257
+ $(ANDROID_BUILD_TOOLS)/aapt package -v -f -m -S $(SRCDIR)/sview/res -J $(BUILD_ROOT)/java/gen -M $(SRCDIR)/sview/AndroidManifest.xml -I $(ANDROID_PLATFORM)
258
259
install_android_libs: $(aStShared) $(aStGLWidgets) $(aStCore) $(aStOutAnaglyph) $(aStOutInterlace) $(aStOutDistorted) $(aStImageViewer) $(aStMoviePlayer) $(sViewAndroid)
260
- cp -f $(BUILD_ROOT)/$(aStShared) $(aDestAndroid)/libs/$(ANDROID_EABI)/
261
- cp -f $(BUILD_ROOT)/$(aStGLWidgets) $(aDestAndroid)/libs/$(ANDROID_EABI)/
262
- cp -f $(BUILD_ROOT)/$(aStCore) $(aDestAndroid)/libs/$(ANDROID_EABI)/
263
- cp -f $(BUILD_ROOT)/$(aStOutAnaglyph) $(aDestAndroid)/libs/$(ANDROID_EABI)/
264
- cp -f $(BUILD_ROOT)/$(aStOutInterlace) $(aDestAndroid)/libs/$(ANDROID_EABI)/
265
- cp -f $(BUILD_ROOT)/$(aStOutDistorted) $(aDestAndroid)/libs/$(ANDROID_EABI)/
266
- cp -f $(BUILD_ROOT)/$(aStImageViewer) $(aDestAndroid)/libs/$(ANDROID_EABI)/
267
- cp -f $(BUILD_ROOT)/$(aStMoviePlayer) $(aDestAndroid)/libs/$(ANDROID_EABI)/
268
- cp -f $(BUILD_ROOT)/$(sViewAndroid) $(aDestAndroid)/libs/$(ANDROID_EABI)/
269
- cp -f $(ANDROID_NDK)/sources/cxx-stl/gnu-libstdc++/4.9/libs/$(ANDROID_EABI)/libgnustl_shared.so $(aDestAndroid)/libs/$(ANDROID_EABI)/
270
- $(STRIP) $(STRIPFLAGS) $(aDestAndroid)/libs/$(ANDROID_EABI)/libgnustl_shared.so
271
- cp -f $(FREETYPE_ROOT)/libs/$(ANDROID_EABI)/libfreetype.so $(aDestAndroid)/libs/$(ANDROID_EABI)/
272
- cp -f $(OPENAL_ROOT)/libs/$(ANDROID_EABI)/libopenal.so $(aDestAndroid)/libs/$(ANDROID_EABI)/
273
- cp -f $(FFMPEG_ROOT)/libs/$(ANDROID_EABI)/libavcodec.so $(aDestAndroid)/libs/$(ANDROID_EABI)/
274
- cp -f $(FFMPEG_ROOT)/libs/$(ANDROID_EABI)/libavdevice.so $(aDestAndroid)/libs/$(ANDROID_EABI)/
275
- cp -f $(FFMPEG_ROOT)/libs/$(ANDROID_EABI)/libavformat.so $(aDestAndroid)/libs/$(ANDROID_EABI)/
276
- cp -f $(FFMPEG_ROOT)/libs/$(ANDROID_EABI)/libavutil.so $(aDestAndroid)/libs/$(ANDROID_EABI)/
277
- cp -f $(FFMPEG_ROOT)/libs/$(ANDROID_EABI)/libswresample.so $(aDestAndroid)/libs/$(ANDROID_EABI)/
278
- cp -f $(FFMPEG_ROOT)/libs/$(ANDROID_EABI)/libswscale.so $(aDestAndroid)/libs/$(ANDROID_EABI)/
279
+ cp -f $(BUILD_ROOT)/$(aStShared) $(aDestAndroid)/lib/$(ANDROID_EABI)/
280
+ cp -f $(BUILD_ROOT)/$(aStGLWidgets) $(aDestAndroid)/lib/$(ANDROID_EABI)/
281
+ cp -f $(BUILD_ROOT)/$(aStCore) $(aDestAndroid)/lib/$(ANDROID_EABI)/
282
+ cp -f $(BUILD_ROOT)/$(aStOutAnaglyph) $(aDestAndroid)/lib/$(ANDROID_EABI)/
283
+ cp -f $(BUILD_ROOT)/$(aStOutInterlace) $(aDestAndroid)/lib/$(ANDROID_EABI)/
284
+ cp -f $(BUILD_ROOT)/$(aStOutDistorted) $(aDestAndroid)/lib/$(ANDROID_EABI)/
285
+ cp -f $(BUILD_ROOT)/$(aStImageViewer) $(aDestAndroid)/lib/$(ANDROID_EABI)/
286
+ cp -f $(BUILD_ROOT)/$(aStMoviePlayer) $(aDestAndroid)/lib/$(ANDROID_EABI)/
287
+ cp -f $(BUILD_ROOT)/$(sViewAndroid) $(aDestAndroid)/lib/$(ANDROID_EABI)/
288
+ cp -f $(ANDROID_NDK)/sources/cxx-stl/gnu-libstdc++/4.9/libs/$(ANDROID_EABI)/libgnustl_shared.so $(aDestAndroid)/lib/$(ANDROID_EABI)/
289
+ $(STRIP) $(STRIPFLAGS) $(aDestAndroid)/lib/$(ANDROID_EABI)/libgnustl_shared.so
290
+ cp -f $(FREETYPE_ROOT)/libs/$(ANDROID_EABI)/libfreetype.so $(aDestAndroid)/lib/$(ANDROID_EABI)/
291
+ cp -f $(OPENAL_ROOT)/libs/$(ANDROID_EABI)/libopenal.so $(aDestAndroid)/lib/$(ANDROID_EABI)/
292
+ cp -f $(FFMPEG_ROOT)/libs/$(ANDROID_EABI)/libavcodec.so $(aDestAndroid)/lib/$(ANDROID_EABI)/
293
+ cp -f $(FFMPEG_ROOT)/libs/$(ANDROID_EABI)/libavdevice.so $(aDestAndroid)/lib/$(ANDROID_EABI)/
294
+ cp -f $(FFMPEG_ROOT)/libs/$(ANDROID_EABI)/libavformat.so $(aDestAndroid)/lib/$(ANDROID_EABI)/
295
+ cp -f $(FFMPEG_ROOT)/libs/$(ANDROID_EABI)/libavutil.so $(aDestAndroid)/lib/$(ANDROID_EABI)/
296
+ cp -f $(FFMPEG_ROOT)/libs/$(ANDROID_EABI)/libswresample.so $(aDestAndroid)/lib/$(ANDROID_EABI)/
297
+ cp -f $(FFMPEG_ROOT)/libs/$(ANDROID_EABI)/libswscale.so $(aDestAndroid)/lib/$(ANDROID_EABI)/
298
299
install_android_cad_libs: $(aStShared) $(aStGLWidgets) $(aStCore) $(aStOutAnaglyph) $(aStOutInterlace) $(aStOutDistorted) $(aStImageViewer) $(aStMoviePlayer) $(sViewAndroidCad)
300
- cp -f $(BUILD_ROOT)/$(aStShared) $(aDestAndroid)/libs/$(ANDROID_EABI)/
301
- cp -f $(BUILD_ROOT)/$(aStGLWidgets) $(aDestAndroid)/libs/$(ANDROID_EABI)/
302
- cp -f $(BUILD_ROOT)/$(aStCore) $(aDestAndroid)/libs/$(ANDROID_EABI)/
303
- cp -f $(BUILD_ROOT)/$(aStOutAnaglyph) $(aDestAndroid)/libs/$(ANDROID_EABI)/
304
- cp -f $(BUILD_ROOT)/$(aStOutInterlace) $(aDestAndroid)/libs/$(ANDROID_EABI)/
305
- cp -f $(BUILD_ROOT)/$(aStOutDistorted) $(aDestAndroid)/libs/$(ANDROID_EABI)/
306
- cp -f $(BUILD_ROOT)/$(aStImageViewer) $(aDestAndroid)/libs/$(ANDROID_EABI)/
307
- cp -f $(BUILD_ROOT)/$(aStMoviePlayer) $(aDestAndroid)/libs/$(ANDROID_EABI)/
308
- cp -f $(BUILD_ROOT)/$(sViewAndroidCad) $(aDestAndroid)/libs/$(ANDROID_EABI)/
309
- cp -f $(FREETYPE_ROOT)/libs/$(ANDROID_EABI)/libfreetype.so $(aDestAndroid)/libs/$(ANDROID_EABI)/
310
- cp -f $(OPENAL_ROOT)/libs/$(ANDROID_EABI)/libopenal.so $(aDestAndroid)/libs/$(ANDROID_EABI)/
311
- cp -f $(FFMPEG_ROOT)/libs/$(ANDROID_EABI)/libavcodec.so $(aDestAndroid)/libs/$(ANDROID_EABI)/
312
- cp -f $(FFMPEG_ROOT)/libs/$(ANDROID_EABI)/libavdevice.so $(aDestAndroid)/libs/$(ANDROID_EABI)/
313
- cp -f $(FFMPEG_ROOT)/libs/$(ANDROID_EABI)/libavformat.so $(aDestAndroid)/libs/$(ANDROID_EABI)/
314
- cp -f $(FFMPEG_ROOT)/libs/$(ANDROID_EABI)/libavutil.so $(aDestAndroid)/libs/$(ANDROID_EABI)/
315
- cp -f $(FFMPEG_ROOT)/libs/$(ANDROID_EABI)/libswresample.so $(aDestAndroid)/libs/$(ANDROID_EABI)/
316
- cp -f $(FFMPEG_ROOT)/libs/$(ANDROID_EABI)/libswscale.so $(aDestAndroid)/libs/$(ANDROID_EABI)/
317
+ cp -f $(BUILD_ROOT)/$(aStShared) $(aDestAndroid)/lib/$(ANDROID_EABI)/
318
+ cp -f $(BUILD_ROOT)/$(aStGLWidgets) $(aDestAndroid)/lib/$(ANDROID_EABI)/
319
+ cp -f $(BUILD_ROOT)/$(aStCore) $(aDestAndroid)/lib/$(ANDROID_EABI)/
320
+ cp -f $(BUILD_ROOT)/$(aStOutAnaglyph) $(aDestAndroid)/lib/$(ANDROID_EABI)/
321
+ cp -f $(BUILD_ROOT)/$(aStOutInterlace) $(aDestAndroid)/lib/$(ANDROID_EABI)/
322
+ cp -f $(BUILD_ROOT)/$(aStOutDistorted) $(aDestAndroid)/lib/$(ANDROID_EABI)/
323
+ cp -f $(BUILD_ROOT)/$(aStImageViewer) $(aDestAndroid)/lib/$(ANDROID_EABI)/
324
+ cp -f $(BUILD_ROOT)/$(aStMoviePlayer) $(aDestAndroid)/lib/$(ANDROID_EABI)/
325
+ cp -f $(BUILD_ROOT)/$(sViewAndroidCad) $(aDestAndroid)/lib/$(ANDROID_EABI)/
326
+ cp -f $(FREETYPE_ROOT)/libs/$(ANDROID_EABI)/libfreetype.so $(aDestAndroid)/lib/$(ANDROID_EABI)/
327
+ cp -f $(OPENAL_ROOT)/libs/$(ANDROID_EABI)/libopenal.so $(aDestAndroid)/lib/$(ANDROID_EABI)/
328
+ cp -f $(FFMPEG_ROOT)/libs/$(ANDROID_EABI)/libavcodec.so $(aDestAndroid)/lib/$(ANDROID_EABI)/
329
+ cp -f $(FFMPEG_ROOT)/libs/$(ANDROID_EABI)/libavdevice.so $(aDestAndroid)/lib/$(ANDROID_EABI)/
330
+ cp -f $(FFMPEG_ROOT)/libs/$(ANDROID_EABI)/libavformat.so $(aDestAndroid)/lib/$(ANDROID_EABI)/
331
+ cp -f $(FFMPEG_ROOT)/libs/$(ANDROID_EABI)/libavutil.so $(aDestAndroid)/lib/$(ANDROID_EABI)/
332
+ cp -f $(FFMPEG_ROOT)/libs/$(ANDROID_EABI)/libswresample.so $(aDestAndroid)/lib/$(ANDROID_EABI)/
333
+ cp -f $(FFMPEG_ROOT)/libs/$(ANDROID_EABI)/libswscale.so $(aDestAndroid)/lib/$(ANDROID_EABI)/
334
mkdir -p $(aDestAndroid)/assets/shaders
335
mkdir -p $(aDestAndroid)/assets/lang
336
337
pre_all:
338
mkdir -p $(BUILD_ROOT)/lang/English
339
+ mkdir -p $(BUILD_ROOT)/lang/Español
340
mkdir -p $(BUILD_ROOT)/lang/русский
341
mkdir -p $(BUILD_ROOT)/lang/français
342
mkdir -p $(BUILD_ROOT)/lang/Deutsch
343
344
mkdir -p $(BUILD_ROOT)/lang/Korean
345
mkdir -p $(BUILD_ROOT)/textures
346
mkdir -p $(BUILD_ROOT)/web
347
- mkdir -p sview/libs/$(ANDROID_EABI)
348
- mkdir -p StCADViewer/libs/$(ANDROID_EABI)
349
cp -f -r textures/* $(BUILD_ROOT)/textures/
350
351
+pre_all_android:
352
+ mkdir -p $(aDestAndroid)/lib/$(ANDROID_EABI)
353
+ mkdir -p $(BUILD_ROOT)/java/gen
354
+ mkdir -p $(BUILD_ROOT)/java/classes
355
+
356
# StShared shared library
357
aStShared_SRCS1 := $(sort $(wildcard $(SRCDIR)/StShared/*.cpp))
358
aStShared_OBJS1 := ${aStShared_SRCS1:.cpp=.o}
359
360
mkdir -p $(BUILD_ROOT)/shaders/StOutAnaglyph/
361
cp -f -r StOutAnaglyph/shaders/* $(BUILD_ROOT)/shaders/StOutAnaglyph/
362
cp -f -r StOutAnaglyph/lang/english/* $(BUILD_ROOT)/lang/English/
363
+ cp -f -r StOutAnaglyph/lang/spanish/* $(BUILD_ROOT)/lang/Español/
364
cp -f -r StOutAnaglyph/lang/russian/* $(BUILD_ROOT)/lang/русский/
365
cp -f -r StOutAnaglyph/lang/french/* $(BUILD_ROOT)/lang/français/
366
cp -f -r StOutAnaglyph/lang/german/* $(BUILD_ROOT)/lang/Deutsch/
367
368
$(LD) -shared $(call libinstname,$@) $(LDFLAGS) $(LIBDIR) $(aStOutDual_OBJS) $(aStOutDual_LIB) -o $(BUILD_ROOT)/$@
369
pre_StOutDual:
370
cp -f -r StOutDual/lang/english/* $(BUILD_ROOT)/lang/English/
371
+ cp -f -r StOutDual/lang/spanish/* $(BUILD_ROOT)/lang/Español/
372
cp -f -r StOutDual/lang/russian/* $(BUILD_ROOT)/lang/русский/
373
cp -f -r StOutDual/lang/french/* $(BUILD_ROOT)/lang/français/
374
cp -f -r StOutDual/lang/german/* $(BUILD_ROOT)/lang/Deutsch/
375
376
mkdir -p $(BUILD_ROOT)/shaders/StOutIZ3D/
377
cp -f -r StOutIZ3D/shaders/* $(BUILD_ROOT)/shaders/StOutIZ3D/
378
cp -f -r StOutIZ3D/lang/english/* $(BUILD_ROOT)/lang/English/
379
+ cp -f -r StOutIZ3D/lang/spanish/* $(BUILD_ROOT)/lang/Español/
380
cp -f -r StOutIZ3D/lang/russian/* $(BUILD_ROOT)/lang/русский/
381
cp -f -r StOutIZ3D/lang/french/* $(BUILD_ROOT)/lang/français/
382
cp -f -r StOutIZ3D/lang/german/* $(BUILD_ROOT)/lang/Deutsch/
383
384
mkdir -p $(BUILD_ROOT)/shaders/StOutInterlace/
385
cp -f -r StOutInterlace/shaders/* $(BUILD_ROOT)/shaders/StOutInterlace/
386
cp -f -r StOutInterlace/lang/english/* $(BUILD_ROOT)/lang/English/
387
+ cp -f -r StOutInterlace/lang/spanish/* $(BUILD_ROOT)/lang/Español/
388
cp -f -r StOutInterlace/lang/russian/* $(BUILD_ROOT)/lang/русский/
389
cp -f -r StOutInterlace/lang/french/* $(BUILD_ROOT)/lang/français/
390
cp -f -r StOutInterlace/lang/german/* $(BUILD_ROOT)/lang/Deutsch/
391
392
$(LD) -shared $(call libinstname,$@) $(LDFLAGS) $(LIBDIR) $(aStOutPageFlip_OBJS1) $(aStOutPageFlip_OBJS2) $(aStOutPageFlip_LIB) -o $(BUILD_ROOT)/$@
393
pre_StOutPageFlip:
394
cp -f -r StOutPageFlip/lang/english/* $(BUILD_ROOT)/lang/English/
395
+ cp -f -r StOutPageFlip/lang/spanish/* $(BUILD_ROOT)/lang/Español/
396
cp -f -r StOutPageFlip/lang/russian/* $(BUILD_ROOT)/lang/русский/
397
cp -f -r StOutPageFlip/lang/french/* $(BUILD_ROOT)/lang/français/
398
cp -f -r StOutPageFlip/lang/german/* $(BUILD_ROOT)/lang/Deutsch/
399
400
$(LD) -shared $(call libinstname,$@) $(LDFLAGS) $(LIBDIR) $(aStOutDistorted_OBJS) $(aStOutDistorted_LIB) -o $(BUILD_ROOT)/$@
401
pre_StOutDistorted:
402
cp -f -r StOutDistorted/lang/english/* $(BUILD_ROOT)/lang/English/
403
+ cp -f -r StOutDistorted/lang/spanish/* $(BUILD_ROOT)/lang/Español/
404
cp -f -r StOutDistorted/lang/russian/* $(BUILD_ROOT)/lang/русский/
405
cp -f -r StOutDistorted/lang/french/* $(BUILD_ROOT)/lang/français/
406
cp -f -r StOutDistorted/lang/german/* $(BUILD_ROOT)/lang/Deutsch/
407
408
$(LD) -shared $(call libinstname,$@) $(LDFLAGS) $(LIBDIR) $(aStImageViewer_OBJS) $(aStImageViewer_LIB) -o $(BUILD_ROOT)/$@
409
pre_StImageViewer:
410
cp -f -r StImageViewer/lang/english/* $(BUILD_ROOT)/lang/English/
411
+ cp -f -r StImageViewer/lang/spanish/* $(BUILD_ROOT)/lang/Español/
412
cp -f -r StImageViewer/lang/russian/* $(BUILD_ROOT)/lang/русский/
413
cp -f -r StImageViewer/lang/french/* $(BUILD_ROOT)/lang/français/
414
cp -f -r StImageViewer/lang/german/* $(BUILD_ROOT)/lang/Deutsch/
415
416
aStMoviePlayer_OBJS2 := ${aStMoviePlayer_SRCS2:.cpp=.o}
417
aStMoviePlayer_SRCS3 := $(sort $(wildcard $(SRCDIR)/StMoviePlayer/*.c))
418
aStMoviePlayer_OBJS3 := ${aStMoviePlayer_SRCS3:.c=.o}
419
-aStMoviePlayer_LIB := $(LIB) -lStGLWidgets -lStShared -lStCore $(LIB_OUTPUTS) $(LIB_GLX) $(LIB_GTK) -lavutil -lavformat -lavcodec -lswscale $(LIB_OPENAL) $(LIB_PTHREAD)
420
+aStMoviePlayer_LIB := $(LIB) -lStGLWidgets -lStShared -lStCore $(LIB_OUTPUTS) $(LIB_GLX) $(LIB_GTK) -lavutil -lavformat -lavcodec -lswscale $(LIB_OPENAL) $(LIB_COREVIDEO) $(LIB_PTHREAD)
421
$(aStMoviePlayer) : pre_StMoviePlayer $(aStGLWidgets) outputs_all $(aStMoviePlayer_OBJS1) $(aStMoviePlayer_OBJS2) $(aStMoviePlayer_OBJS3)
422
$(LD) -shared $(call libinstname,$@) $(LDFLAGS) $(LIBDIR) $(aStMoviePlayer_OBJS1) $(aStMoviePlayer_OBJS2) $(aStMoviePlayer_OBJS3) $(aStMoviePlayer_LIB) -o $(BUILD_ROOT)/$@
423
pre_StMoviePlayer:
424
cp -f -r StMoviePlayer/lang/english/* $(BUILD_ROOT)/lang/English/
425
+ cp -f -r StMoviePlayer/lang/spanish/* $(BUILD_ROOT)/lang/Español/
426
cp -f -r StMoviePlayer/lang/russian/* $(BUILD_ROOT)/lang/русский/
427
cp -f -r StMoviePlayer/lang/french/* $(BUILD_ROOT)/lang/français/
428
cp -f -r StMoviePlayer/lang/german/* $(BUILD_ROOT)/lang/Deutsch/
429
430
$(LD) -shared $(call libinstname,$@) $(LDFLAGS) $(LIBDIR) $(aStDiagnostics_OBJS) $(aStDiagnostics_LIB) -o $(BUILD_ROOT)/$@
431
pre_StDiagnostics:
432
cp -f -r StDiagnostics/lang/english/* $(BUILD_ROOT)/lang/English/
433
+ cp -f -r StDiagnostics/lang/spanish/* $(BUILD_ROOT)/lang/Español/
434
cp -f -r StDiagnostics/lang/russian/* $(BUILD_ROOT)/lang/русский/
435
cp -f -r StDiagnostics/lang/french/* $(BUILD_ROOT)/lang/français/
436
cp -f -r StDiagnostics/lang/german/* $(BUILD_ROOT)/lang/Deutsch/
437
438
$(LD) -shared $(call libinstname,$@) $(LDFLAGS) $(LIBDIR) $(aStCADViewer_OBJS) $(aStCADViewer_LIB) -o $(BUILD_ROOT)/$@
439
pre_StCADViewer:
440
cp -f -r StCADViewer/lang/english/* $(BUILD_ROOT)/lang/English/
441
+ cp -f -r StCADViewer/lang/spanish/* $(BUILD_ROOT)/lang/Español/
442
cp -f -r StCADViewer/lang/russian/* $(BUILD_ROOT)/lang/русский/
443
cp -f -r StCADViewer/lang/french/* $(BUILD_ROOT)/lang/français/
444
cp -f -r StCADViewer/lang/german/* $(BUILD_ROOT)/lang/Deutsch/
445
446
clean_sViewAndroid:
447
rm -f $(BUILD_ROOT)/$(sViewAndroid)
448
rm -rf sview/jni/*.o
449
+ rm -rf $(BUILD_ROOT)/java/classes/com/sview/*.class
450
+ rm -rf $(SRCDIR)/sview/src/com/sview/*class
451
+ rm -rf $(aDestAndroid)
452
+ rm -f $(sViewDex)
453
+ rm -f $(sViewApkUnsigned)
454
+ rm -f $(sViewApkSigned)
455
+ rm -f $(sViewApk)
456
+ rm -rf $(BUILD_ROOT)/java/gen/com/sview/*.java
457
458
# sView executable
459
sView_SRCS1 := $(sort $(wildcard $(SRCDIR)/sview/*.cpp))
460
461
cp -R -f $(FFMPEG_ROOT)/$(LIBSUBFOLDER)/libswscale*.dylib $(BUILD_ROOT_BUNDLE)/Contents/Frameworks
462
endif
463
ifneq ($(OPENAL_ROOT),)
464
+ mkdir -p $(BUILD_ROOT_BUNDLE)/Contents/MacOS/openal/hrtf/
465
cp -R -f $(OPENAL_ROOT)/$(LIBSUBFOLDER)/libopenal*.dylib $(BUILD_ROOT_BUNDLE)/Contents/Frameworks
466
+ cp -f -r $(OPENAL_ROOT)/hrtf/*.mhr $(BUILD_ROOT_BUNDLE)/Contents/MacOS/openal/hrtf/
467
endif
468
endif
469
@echo sView building is DONE
470
471
+$(sViewApk): $(sViewApkSigned)
472
+ $(ANDROID_BUILD_TOOLS)/zipalign -v -f 4 $< $(sViewApk)
473
+
474
+# There are three options:
475
+# 1) Passwords are specified within Makefile / passed as make arguments
476
+# 2) Passwords are asked by jarsigner itself (requires console input)
477
+# 3) Passwords are asked using zenity message window (requires GUI input)
478
+ifeq ($(MAKECMDGOALS), android)
479
+
480
+ifeq ($(ANDROID_KEY_GUI), 1)
481
+$(sViewApkSigned): $(sViewApkUnsigned) sView_keystore_debug
482
+ $(eval ANDROID_KEYSTORE_PASSWORD := $(shell zenity --password --title="Android keystore"))
483
+ $(eval ANDROID_KEY_PASSWORD := $(shell zenity --password --title="Android key"))
484
+ $(JAVA_HOME)/bin/jarsigner -verbose -sigalg SHA1withRSA -digestalg SHA1 -keystore $(ANDROID_KEYSTORE) -storepass $(ANDROID_KEYSTORE_PASSWORD) -keypass $(ANDROID_KEY_PASSWORD) -signedjar $(sViewApkSigned) $< $(ANDROID_KEY)
485
+else ifeq ($(ANDROID_KEY_PASSWORD),)
486
+$(sViewApkSigned): $(sViewApkUnsigned) sView_keystore_debug
487
+ $(JAVA_HOME)/bin/jarsigner -verbose -sigalg SHA1withRSA -digestalg SHA1 -keystore $(ANDROID_KEYSTORE) -signedjar $(sViewApkSigned) $< $(ANDROID_KEY)
488
+else
489
+$(sViewApkSigned): $(sViewApkUnsigned) sView_keystore_debug
490
+ $(JAVA_HOME)/bin/jarsigner -verbose -sigalg SHA1withRSA -digestalg SHA1 -keystore $(ANDROID_KEYSTORE) -storepass $(ANDROID_KEYSTORE_PASSWORD) -keypass $(ANDROID_KEY_PASSWORD) -signedjar $(sViewApkSigned) $< $(ANDROID_KEY)
491
+endif
492
+endif
493
+
494
+$(sViewApkUnsigned): $(sViewDex) install_android_libs
495
+ rm -f $(sViewApkUnsigned)
496
+ $(ANDROID_BUILD_TOOLS)/aapt package -v -f -M $(SRCDIR)/sview/AndroidManifest.xml -S $(SRCDIR)/sview/res -I $(ANDROID_PLATFORM) -F $(sViewApkUnsigned) $(aDestAndroid)
497
+
498
+sView_SRCS_JAVA1 := $(sort $(wildcard $(SRCDIR)/sview/src/com/sview/*.java))
499
+sView_OBJS_JAVA1 := ${sView_SRCS_JAVA1:.java=.class}
500
+$(sViewDex): $(BUILD_ROOT)/java/gen/com/sview/R.class $(sView_OBJS_JAVA1)
501
+ $(ANDROID_BUILD_TOOLS)/dx --dex --verbose --output=$(sViewDex) $(BUILD_ROOT)/java/classes
502
+
503
+$(BUILD_ROOT)/java/gen/com/sview/R.java: install_android $(shell find $(SRCDIR)/sview/res -type f)
504
+ $(ANDROID_BUILD_TOOLS)/aapt package -v -f -m -S $(SRCDIR)/sview/res -J $(BUILD_ROOT)/java/gen -M $(SRCDIR)/sview/AndroidManifest.xml -I $(ANDROID_PLATFORM)
505
+
506
+# This target generates a dummy signing key for debugging purposes.
507
+# Executed only when ANDROID_KEYSTORE points to non-existing file.
508
+ifeq (,$(wildcard $(ANDROID_KEYSTORE)))
509
+sView_keystore_debug:
510
+ $(JAVA_HOME)/bin/keytool -genkeypair -validity 1000 -dname "CN=sview_dummy,O=Android,C=JPN" -keystore $(ANDROID_KEYSTORE) \
511
+ -storepass $(ANDROID_KEYSTORE_PASSWORD) -keypass $(ANDROID_KEY_PASSWORD) -alias $(ANDROID_KEY) -keyalg RSA -v
512
+else
513
+sView_keystore_debug:
514
+endif
515
516
clean_sView:
517
rm -f $(BUILD_ROOT)/$(sView)
518
sview-17_04.tar.gz/StBrowserPlugin/StBrowserPlugin.rc -> sview-20_08.tar.gz/StBrowserPlugin/StBrowserPlugin.rc
Changed
10
1
2
VALUE "FileOpenName", ST_NPAPI_MIME_DESC
3
VALUE "FileVersion", SVIEW_SDK_VER_STRING "\000"
4
VALUE "InternalName", "StBrowserPlugin\000"
5
- VALUE "LegalCopyright", "\251 2009-2016 Kirill Gavrilov\000"
6
+ VALUE "LegalCopyright", "\251 2009-2020 Kirill Gavrilov\000"
7
VALUE "LegalTrademarks", "\000"
8
VALUE "MIMEType", ST_NPAPI_MIME_LIST
9
VALUE "OriginalFilename", "npStBrowserPlugin.dll\000"
10
sview-17_04.tar.gz/StCADViewer/StCADViewer.rc -> sview-20_08.tar.gz/StCADViewer/StCADViewer.rc
Changed
10
1
2
BEGIN
3
VALUE "FileDescription", "Stereoscopic CAD Viewer\000"
4
VALUE "FileVersion", SVIEW_SDK_VER_STRING "\000"
5
- VALUE "LegalCopyright", "\251 2011-2017 Kirill Gavrilov\000"
6
+ VALUE "LegalCopyright", "\251 2011-2020 Kirill Gavrilov\000"
7
VALUE "ProductName", "StCADViewer\000"
8
VALUE "ProductVersion", SVIEW_SDK_VER_STRING "\000"
9
VALUE "OfficialSite", "www.sview.ru\000"
10
sview-17_04.tar.gz/StCADViewer/StCADViewerGUI.cpp -> sview-20_08.tar.gz/StCADViewer/StCADViewerGUI.cpp
Changed
10
1
2
const StGLVec3 THE_WHITE(1.0f, 1.0f, 1.0f);
3
const StString anAbout = tr(ABOUT_DPLUGIN_NAME) + '\n'
4
+ tr(ABOUT_VERSION) + " " + StVersionInfo::getSDKVersionString()
5
- + "\n \n" + tr(ABOUT_DESCRIPTION).format("2011-2017", "kirill@sview.ru", "www.sview.ru");
6
+ + "\n \n" + tr(ABOUT_DESCRIPTION).format("2011-2020", "kirill@sview.ru", "www.sview.ru");
7
8
StArgumentsMap anInfo;
9
anInfo.add(StDictEntry("CPU cores", StString(StThread::countLogicalProcessors()) + StString(" logical processor(s)")));
10
sview-20_08.tar.gz/StCADViewer/lang/spanish
Added
2
1
+(directory)
2
sview-20_08.tar.gz/StCADViewer/lang/spanish/StCADViewer.lng
Added
29
1
2
+# Spanish translation file for StCADViewer
3
+--------
4
+1200=Ver
5
+1202=Pantalla completa
6
+1204=Mostrar triedro
7
+1206=Proyección
8
+1208=Ajustar TODO
9
+1240=Ortogonal
10
+1241=Perspectiva
11
+1242=Estéreo
12
+1402=Mostrar FPS
13
+1500=Ayuda
14
+1501=Acerca de...
15
+1503=Texto de la licencia
16
+1504=Idioma (Language)
17
+1511=Ajustes
18
+3000=sView - Mini visor de CAD
19
+3001=versión
20
+3002=El visualizador CAD te permite ver archivos CAD en formatos IGES, STEP y BREP usando tecnología OpenCASCADE.\n © {0} Kirill Gavrilov <{1}>\nSitio oficial: {2}\n\nEste programa se distribuye bajo licencia GPL 3.0
21
+3004=Información del sistema
22
+4000=Cerrar
23
+4001=Cancelar
24
+4006=Guardar
25
+4007=Eliminar
26
+4008=Predeterminado
27
+4009=Predeterminados
28
+4010=Asignar
29
sview-17_04.tar.gz/StCore/StAndroidGlue.cpp -> sview-20_08.tar.gz/StCore/StAndroidGlue.cpp
Changed
262
1
2
#include <StStrings/StLogger.h>
3
4
#include <StAV/stAV.h>
5
+#include <StJNI/StJNIEnv.h>
6
7
#include <android/window.h>
8
9
-#define jexp extern "C" JNIEXPORT
10
-
11
-StJNIEnv::StJNIEnv(JavaVM* theJavaVM)
12
-: myJavaVM(theJavaVM),
13
- myJniEnv(NULL),
14
- myToDetach(false) {
15
- if(myJavaVM == NULL) {
16
- return;
17
- }
18
-
19
- void* aJniEnv = NULL;
20
- switch(myJavaVM->GetEnv(&aJniEnv, JNI_VERSION_1_6)) {
21
- case JNI_EDETACHED: {
22
- if(myJavaVM->AttachCurrentThread(&myJniEnv, NULL) < 0) {
23
- myJniEnv = NULL;
24
- ST_ERROR_LOG("Failed to attach working thread to Java VM");
25
- return;
26
- }
27
- myToDetach = true;
28
- break;
29
- }
30
- case JNI_OK: {
31
- myJniEnv = (JNIEnv* )aJniEnv;
32
- myToDetach = false;
33
- break;
34
- }
35
- case JNI_EVERSION: {
36
- ST_ERROR_LOG("Failed to attach working thread to Java VM - JNI version is not supported");
37
- break;
38
- }
39
- default: {
40
- ST_ERROR_LOG("Failed to attach working thread to Java VM");
41
- break;
42
- }
43
- }
44
-}
45
-
46
-StJNIEnv::~StJNIEnv() {
47
- detach();
48
-}
49
+#include "stvkeysandroid.h" // Android NDK keys to VKEYs lookup array
50
51
-void StJNIEnv::detach() {
52
- if(myJavaVM != NULL
53
- && myJniEnv != NULL
54
- && myToDetach) {
55
- myJavaVM->DetachCurrentThread();
56
- }
57
-
58
- myJniEnv = NULL;
59
- myToDetach = false;
60
-}
61
+#define jexp extern "C" JNIEXPORT
62
63
StAndroidResourceManager::StAndroidResourceManager(StAndroidGlue* theGlueApp,
64
const StString& theAppName)
65
66
myWindow(NULL),
67
myWindowPending(NULL),
68
myIsChangingSurface(false),
69
+ myIsWakeLockSet(false),
70
myWindowFlags(0),
71
myActivityState(0),
72
myMemoryClassMiB(0),
73
74
myIsRunning(false),
75
myIsStateSaved(false),
76
myToDestroy(false) {
77
+ stMemZero(myRegKeys, sizeof(myRegKeys));
78
theActivity->instance = this;
79
theActivity->env->GetJavaVM(&myJavaVM);
80
81
82
myMemoryClassMiB = aJniEnv->CallIntMethod(aJActivityMgr, aJMet_getMemoryClass);
83
}
84
85
+ if(jclass aClassBuild = aJniEnv->FindClass("android/os/Build")) {
86
+ if(jfieldID aJFieldModel = aJniEnv->GetStaticFieldID(aClassBuild, "MODEL", "Ljava/lang/String;")) {
87
+ myBuildModel = stStringFromJava(aJniEnv, (jstring )aJniEnv->GetStaticObjectField(aClassBuild, aJFieldModel));
88
+ }
89
+ if(jfieldID aJFieldDevice = aJniEnv->GetStaticFieldID(aClassBuild, "DEVICE", "Ljava/lang/String;")) {
90
+ myBuildDevice = stStringFromJava(aJniEnv, (jstring )aJniEnv->GetStaticObjectField(aClassBuild, aJFieldDevice));
91
+ }
92
+ }
93
+
94
jmethodID aJMet_getStAppClass = aJniEnv->GetMethodID(aJClass_Activity, "getStAppClass", "()Ljava/lang/String;");
95
myStAppClass = stStringFromJava(aJniEnv, (jstring )aJniEnv->CallObjectMethod(myActivity->clazz, aJMet_getStAppClass));
96
97
98
jmethodID aJMet_setCppInstance = aJniEnv->GetMethodID(aJClass_Activity, "setCppInstance", "(J)V");
99
aJniEnv->CallVoidMethod(myActivity->clazz, aJMet_setCppInstance, (jlong )this);
100
101
- readOpenPath();
102
+ // do not NULLify intent here since Activity.onCreate() crashes on some devices
103
+ readOpenPath(false);
104
105
myCmdPollSource.id = LooperId_MAIN;
106
myCmdPollSource.app = this;
107
108
myMsgWrite = aMsgPipe[1];
109
}
110
111
-void StAndroidGlue::readOpenPath() {
112
+void StAndroidGlue::readOpenPath(bool theToNullifyIntent) {
113
JNIEnv* aJniEnv = myActivity->env;
114
jclass aJClass_Activity = aJniEnv->GetObjectClass(myActivity->clazz);
115
- jmethodID aJMet_readOpenPath = aJniEnv->GetMethodID(aJClass_Activity, "readOpenPath", "()V");
116
- aJniEnv->CallVoidMethod(myActivity->clazz, aJMet_readOpenPath);
117
+ jmethodID aJMet_readOpenPath = aJniEnv->GetMethodID(aJClass_Activity, "readOpenPath", "(Z)V");
118
+ aJniEnv->CallVoidMethod(myActivity->clazz, aJMet_readOpenPath, (jboolean )(theToNullifyIntent ? JNI_TRUE : JNI_FALSE));
119
}
120
121
void StAndroidGlue::setOpenPath(const jstring theOpenPath,
122
123
124
void StAndroidGlue::fetchState(StString& theNewFile,
125
StQuaternion<double>& theQuaternion,
126
- bool& theToSwapEyes) {
127
+ bool& theToSwapEyes,
128
+ const StKeysState& theKeys) {
129
StMutexAuto aLock(myFetchLock);
130
+ stMemCpy(myRegKeys, theKeys.getRegisteredKeys(), sizeof(myRegKeys));
131
+
132
theQuaternion = myQuaternion;
133
theToSwapEyes = myToSwapEyesHW;
134
if(!myDndPath.isEmpty()) {
135
136
137
StMonitor aMon;
138
aMon.setId(0);
139
+
140
+ const StString aBuildDevice = myBuildDevice.lowerCased();
141
+ const StString aBuildModel = myBuildModel.lowerCased();
142
if(myStereoApiId == "S3DV") {
143
aMon.setPnPId("ST@S3DV");
144
+ } else if(aBuildDevice == "king7s" || aBuildModel == "pp6000") { // PPTV King 7S
145
+ aMon.setPnPId("ST@COL0");
146
+ } else if(aBuildModel == "y6 max 3d") { // DOOGEE Y6 Max 3D
147
+ aMon.setPnPId("ST@COL0");
148
+ } else if(aBuildModel == "p8 3d" || aBuildModel == "p8_3d") { // Elephone P8 3D
149
+ aMon.setPnPId("ST@COL0");
150
}
151
aMon.changeVRect().top() = 0;
152
aMon.changeVRect().left() = 0;
153
154
postMessage("jp.co.sharp.android.stereo3dlcd !!!");
155
}*/
156
157
- createApplication();
158
- if(!myApp.isNull()) {
159
- if(!myApp->open()) {
160
+ for(;;) {
161
+ createApplication();
162
+ if(myApp.isNull()) {
163
+ stError("Error: no application to execute!");
164
+ break;
165
+ } else if(!myApp->open()) {
166
stError("Error: application can not be executed!");
167
+ break;
168
}
169
myApp->exec();
170
- } else {
171
- stError("Error: no application to execute!");
172
+
173
+ StHandle<StOpenInfo> anOther = myApp->getOpenFileInOtherDrawer();
174
+ if(anOther.isNull()) {
175
+ break;
176
+ }
177
+
178
+ myApp.nullify();
179
+ StArgument aDrawerArg = anOther->getArgumentsMap()["in"];
180
+ myDndPath = anOther->getPath();
181
+ myStAppClass = aDrawerArg.getValue();
182
}
183
myApp.nullify();
184
185
186
187
void StAndroidGlue::setActivityState(int8_t theState) {
188
if(theState == StAndroidGlue::CommandId_Resume) {
189
- readOpenPath();
190
+ readOpenPath(true);
191
}
192
193
pthread_mutex_lock(&myMutex);
194
195
ANativeActivity_setWindowFlags(myActivity, aFlagsToAdd, aFlagsToRemove);
196
}
197
198
+void StAndroidGlue::setWakeLock(const StString& theTitle, bool theToLock) {
199
+ if((myIsWakeLockSet == theToLock
200
+ && myWakeLockTitle == theTitle)
201
+ || myThJniEnv == NULL) {
202
+ return;
203
+ }
204
+
205
+ jclass aJClassActivity = myThJniEnv->GetObjectClass(myActivity->clazz);
206
+ jmethodID aJMet = myThJniEnv->GetMethodID(aJClassActivity, "setPartialWakeLockOn", "(Ljava/lang/String;Z)V");
207
+ jstring aJStrTitle = myThJniEnv->NewStringUTF(theTitle.toCString());
208
+ myThJniEnv->CallVoidMethod(myActivity->clazz, aJMet, aJStrTitle, (jboolean )(theToLock ? JNI_TRUE : JNI_FALSE));
209
+ myIsWakeLockSet = theToLock;
210
+ myThJniEnv->DeleteLocalRef(aJStrTitle);
211
+ myWakeLockTitle = theTitle;
212
+}
213
+
214
+void StAndroidGlue::setWindowTitle(const StString& theTitle) {
215
+ if(myWindowTitle == theTitle
216
+ || myThJniEnv == NULL) {
217
+ return;
218
+ }
219
+
220
+ jclass aJClassActivity = myThJniEnv->GetObjectClass(myActivity->clazz);
221
+ jmethodID aJMet = myThJniEnv->GetMethodID(aJClassActivity, "setWindowTitle", "(Ljava/lang/String;)V");
222
+ jstring aJStrTitle = myThJniEnv->NewStringUTF(theTitle.toCString());
223
+ myThJniEnv->CallVoidMethod(myActivity->clazz, aJMet, aJStrTitle);
224
+ myThJniEnv->DeleteLocalRef(aJStrTitle);
225
+ myWindowTitle = theTitle;
226
+}
227
+
228
void StAndroidGlue::setHardwareStereoOn(const bool theToEnable) {
229
if(myToEnableStereoHW == theToEnable
230
|| myStereoApiId.isEmpty()
231
232
myToSwapEyesHW = theToSwapLR;
233
}
234
235
+bool StAndroidGlue::isKeyOverridden(int theKeyCode) {
236
+ StVirtKey aVKeySt = ST_VK_NULL;
237
+ if(theKeyCode < ST_ANDROID2ST_VK_SIZE) {
238
+ aVKeySt = (StVirtKey )ST_ANDROID2ST_VK[theKeyCode];
239
+ }
240
+
241
+ if(aVKeySt <= 0 || (int )aVKeySt >= ST_VK_NB) {
242
+ return false;
243
+ }
244
+
245
+ StMutexAuto aLock(myFetchLock);
246
+ return myRegKeys[aVKeySt];
247
+}
248
+
249
jexp void JNICALL Java_com_sview_StActivity_cppSetOpenPath(JNIEnv* theEnv, jobject theObj, jlong theCppPtr,
250
jstring theOpenPath, jstring theMimeType, jboolean theIsLaunchedFromHistory) {
251
((StAndroidGlue* )theCppPtr)->setOpenPath(theOpenPath, theMimeType, theIsLaunchedFromHistory);
252
253
((StAndroidGlue* )theCppPtr)->setSwapEyes(theToSwap == JNI_TRUE);
254
}
255
256
+jexp jboolean JNICALL Java_com_sview_StActivity_cppIsKeyOverridden(JNIEnv* theEnv, jobject theObj, jlong theCppPtr,
257
+ jint theKeyCode) {
258
+ return ((StAndroidGlue* )theCppPtr)->isKeyOverridden(theKeyCode);
259
+}
260
+
261
#endif // __ANDROID__
262
sview-17_04.tar.gz/StCore/StApplication.cpp -> sview-20_08.tar.gz/StCore/StApplication.cpp
Changed
137
1
2
/**
3
* StCore, window system independent C++ toolkit for writing OpenGL applications.
4
- * Copyright © 2009-2016 Kirill Gavrilov <kirill@sview.ru>
5
+ * Copyright © 2009-2017 Kirill Gavrilov <kirill@sview.ru>
6
*
7
* Distributed under the Boost Software License, Version 1.0.
8
* See accompanying file license-boost.txt or copy at
9
10
#include "StEventsBuffer.h"
11
12
namespace {
13
+
14
static const StCString ST_SETTING_RENDERER_AUTO = stCString("rendererPluginAuto");
15
static const StCString ST_SETTING_RENDERER = stCString("rendererPlugin");
16
static const StCString ST_SETTING_AUTO_VALUE = stCString("Auto");
17
+ static const StCString ST_SETTING_DEF_DRAWER = stCString("defaultDrawer");
18
+
19
+ /**
20
+ * Auxiliary parameter.
21
+ */
22
+ class StDefaultDrawerParam : public StBoolParamNamed {
23
+
24
+ public:
25
+
26
+ /**
27
+ * Main constructor.
28
+ */
29
+ StDefaultDrawerParam(const StApplication* theApp, const StString& theDrawer, const StString& theTitle)
30
+ : StBoolParamNamed(theApp->isDefaultDrawer(theDrawer), StString(), theTitle),
31
+ myApp(theApp), myAppName(theDrawer) {}
32
+
33
+ /**
34
+ * Return list of available translations.
35
+ */
36
+ virtual bool setValue(const bool theValue) ST_ATTR_OVERRIDE {
37
+ const bool aResult = StBoolParamNamed::setValue(theValue);
38
+ myApp->setDefaultDrawer(theValue ? myAppName : StString());
39
+ return aResult;
40
+ }
41
+
42
+ private:
43
+
44
+ const StApplication* myApp;
45
+ StString myAppName;
46
+
47
+ };
48
+
49
}
50
51
void StApplication::doChangeDevice(const int32_t theValue) {
52
53
54
void StApplication::registerHotKeys() {
55
myKeyActions.clear();
56
+ StKeysState* aKeysState = !myWindow.isNull() ? &myWindow->changeKeysState() : NULL;
57
+ if(aKeysState != NULL) {
58
+ aKeysState->resetRegisteredKeys();
59
+ }
60
for(std::map< int, StHandle<StAction> >::iterator anIter = myActions.begin();
61
anIter != myActions.end(); ++anIter) {
62
const StHandle<StAction>& anAction = anIter->second;
63
- if(anAction->getHotKey1() != 0) {
64
- StHandle<StAction> anOldAction = getActionForKey(anAction->getHotKey1());
65
- if(!anOldAction.isNull()) {
66
- anOldAction->setHotKey1(0);
67
+ for(int aHotIter = 0; aHotIter < 2; ++aHotIter) {
68
+ const unsigned int aHotKey = anAction->getHotKey(aHotIter);
69
+ if(aHotKey == 0) {
70
+ continue;
71
}
72
- myKeyActions[anAction->getHotKey1()] = anAction;
73
- }
74
- if(anAction->getHotKey2() != 0) {
75
- StHandle<StAction> anOldAction = getActionForKey(anAction->getHotKey2());
76
+
77
+ StHandle<StAction> anOldAction = getActionForKey(aHotKey);
78
if(!anOldAction.isNull()) {
79
- anOldAction->setHotKey2(0);
80
+ for(int anOldHotIter = 0; anOldHotIter < 2; ++anOldHotIter) {
81
+ if(anOldAction->getHotKey(anOldHotIter) == aHotKey) {
82
+ anOldAction->setHotKey(anOldHotIter, 0);
83
+ }
84
+ }
85
+ }
86
+ myKeyActions[aHotKey] = anAction;
87
+ if(aKeysState != NULL) {
88
+ const StVirtKey aVirtKey = getBaseKeyFromHotKey(aHotKey);
89
+ aKeysState->registerKey(aVirtKey);
90
}
91
- myKeyActions[anAction->getHotKey2()] = anAction;
92
}
93
}
94
}
95
96
return anInfo;
97
}
98
99
+bool StApplication::isDefaultDrawer(const StString& theDrawer) const {
100
+ StSettings aGlobalSettings(myResMgr, "sview");
101
+ StString aDefDrawer;
102
+ aGlobalSettings.loadString(ST_SETTING_DEF_DRAWER, aDefDrawer);
103
+ return theDrawer == aDefDrawer;
104
+}
105
+
106
+void StApplication::setDefaultDrawer(const StString& theDrawer) const {
107
+ StSettings aGlobalSettings(myResMgr, "sview");
108
+ aGlobalSettings.saveString(ST_SETTING_DEF_DRAWER, theDrawer);
109
+}
110
+
111
+bool StApplication::readDefaultDrawer(StHandle<StOpenInfo>& theInfo) {
112
+ StHandle<StResourceManager> aResMgr = new StResourceManager();
113
+ StSettings aGlobalSettings(aResMgr, "sview");
114
+ StString aDefDrawer;
115
+ aGlobalSettings.loadString(ST_SETTING_DEF_DRAWER, aDefDrawer);
116
+ if(aDefDrawer.isEmpty()) {
117
+ return false;
118
+ }
119
+
120
+ if(theInfo.isNull()) {
121
+ theInfo = new StOpenInfo();
122
+ }
123
+ StArgumentsMap anArgs = theInfo->getArgumentsMap();
124
+ anArgs.add(StArgument("in", aDefDrawer));
125
+ theInfo->setArgumentsMap(anArgs);
126
+ return true;
127
+}
128
+
129
+StHandle<StBoolParamNamed> StApplication::createDefaultDrawerParam(const StString& theDrawer,
130
+ const StString& theTitle) const {
131
+ return new StDefaultDrawerParam(this, theDrawer, theTitle);
132
+}
133
+
134
void StApplication::doChangeLanguage(const int32_t ) {
135
myToRecreateMenu = true;
136
myLangMap->resetReloaded();
137
sview-17_04.tar.gz/StCore/StCocoaView.h -> sview-20_08.tar.gz/StCore/StCocoaView.h
Changed
17
1
2
3
class StWindowImpl;
4
5
+ST_DISABLE_DEPRECATION_WARNINGS
6
@interface StCocoaView : NSOpenGLView
7
{
8
StWindowImpl* myStWin; //!< pointer to StWindowImpl instance
9
10
bool myToHideCursor;
11
bool myIsLionOS;
12
}
13
+ST_ENABLE_DEPRECATION_WARNINGS
14
15
/**
16
* Main constructor.
17
sview-17_04.tar.gz/StCore/StCocoaView.mm -> sview-20_08.tar.gz/StCore/StCocoaView.mm
Changed
44
1
2
- (id ) initWithStWin: (StWindowImpl* ) theStWin
3
nsWin: (NSWindow* ) theNsWin {
4
NSRect aBounds = [[theNsWin contentView] bounds];
5
+ ST_DISABLE_DEPRECATION_WARNINGS
6
self = [super initWithFrame: aBounds
7
pixelFormat: [[NSOpenGLView class] defaultPixelFormat]];
8
+ ST_ENABLE_DEPRECATION_WARNINGS
9
if(self == NULL) {
10
return NULL;
11
}
12
13
14
// enable HiDPI mode
15
if(myIsLionOS) {
16
+ ST_DISABLE_DEPRECATION_WARNINGS
17
[self setWantsBestResolutionOpenGLSurface: YES];
18
+ ST_ENABLE_DEPRECATION_WARNINGS
19
}
20
21
// create blank cursor
22
23
CGFloat aDeltaY = [theEvent deltaY];
24
if(!stAreEqual(aDeltaX, 0.0f, 0.01f)) {
25
myStEvent.Scroll.StepsX = aDeltaX > 0.0f ? -1 : 1;
26
- myStEvent.Scroll.DeltaX = 10.0f * myStEvent.Scroll.StepsX;
27
+ myStEvent.Scroll.DeltaX = myStEvent.Scroll.StepsX;
28
}
29
if(!stAreEqual(aDeltaY, 0.0f, 0.01f)) {
30
myStEvent.Scroll.StepsY = aDeltaY > 0.0f ? 1 : -1;
31
- myStEvent.Scroll.DeltaY = 10.0f * myStEvent.Scroll.StepsY;
32
+ myStEvent.Scroll.DeltaY = myStEvent.Scroll.StepsY;
33
}
34
35
if(myIsLionOS
36
&& [theEvent hasPreciseScrollingDeltas]) {
37
- myStEvent.Scroll.DeltaX = [theEvent scrollingDeltaX];
38
- myStEvent.Scroll.DeltaY = [theEvent scrollingDeltaY];
39
+ myStEvent.Scroll.DeltaX = 0.1f * [theEvent scrollingDeltaX];
40
+ myStEvent.Scroll.DeltaY = 0.1f * [theEvent scrollingDeltaY];
41
}
42
43
//if([theEvent subtype] == NSMouseEventSubtype) {
44
sview-17_04.tar.gz/StCore/StCore.rc -> sview-20_08.tar.gz/StCore/StCore.rc
Changed
10
1
2
BEGIN
3
VALUE "FileDescription", "sView core library\000"
4
VALUE "FileVersion", SVIEW_SDK_VER_STRING "\000"
5
- VALUE "LegalCopyright", "\251 2007-2017 Kirill Gavrilov\000"
6
+ VALUE "LegalCopyright", "\251 2007-2020 Kirill Gavrilov and sView developers\000"
7
VALUE "ProductName", "StCore\000"
8
VALUE "ProductVersion", SVIEW_SDK_VER_STRING "\000"
9
VALUE "OfficialSite", "www.sview.ru\000"
10
sview-17_04.tar.gz/StCore/StKeysState.cpp -> sview-20_08.tar.gz/StCore/StKeysState.cpp
Changed
37
1
2
/**
3
* StCore, window system independent C++ toolkit for writing OpenGL applications.
4
- * Copyright © 2013 Kirill Gavrilov <kirill@sview.ru>
5
+ * Copyright © 2013-2017 Kirill Gavrilov <kirill@sview.ru>
6
*
7
* Distributed under the Boost Software License, Version 1.0.
8
* See accompanying file license-boost.txt or copy at
9
10
#include <StCore/StKeysState.h>
11
12
StKeysState::StKeysState() {
13
- stMemZero(myKeys, sizeof(myKeys));
14
+ stMemZero(myKeys, sizeof(myKeys));
15
+ stMemZero(myRegKeys, sizeof(myRegKeys));
16
}
17
18
StKeysState::~StKeysState() {
19
//
20
}
21
22
+void StKeysState::resetRegisteredKeys() {
23
+ stMemZero(myRegKeys, sizeof(myRegKeys));
24
+}
25
+
26
+void StKeysState::registerKey(StVirtKey theKey) {
27
+ myRegKeys[theKey] = true;
28
+}
29
+
30
+void StKeysState::unregisterKey(StVirtKey theKey) {
31
+ myRegKeys[theKey] = false;
32
+}
33
+
34
void StKeysState::reset() {
35
StMutexAuto aLock(myLock);
36
stMemZero(myKeys, sizeof(myKeys));
37
sview-17_04.tar.gz/StCore/StSearchMonitors.cpp -> sview-20_08.tar.gz/StCore/StSearchMonitors.cpp
Changed
31
1
2
StRectI_t stRect(monInfo.rcMonitor.top, monInfo.rcMonitor.bottom, monInfo.rcMonitor.left, monInfo.rcMonitor.right);
3
aMon.setVRect(stRect);
4
aMon.setId(monCount);
5
- aMon.setFreq((int )dm.dmDisplayFrequency);
6
+ aMon.setFreq((float )dm.dmDisplayFrequency);
7
// TODO
8
- aMon.setFreqMax((int )dm.dmDisplayFrequency);
9
+ aMon.setFreqMax((float )dm.dmDisplayFrequency);
10
11
// ddMon.DeviceString = "Plug and Play monitor"
12
// ddMon.DeviceName = "\\.\DISPLAY2\Monitor0"
13
14
break;
15
}
16
double aRate = std::floor(double(aMode.dotClock) / (double(aMode.hTotal) * double(aMode.vTotal)) + 0.5);
17
- aMonitor.setFreq(int(aRate));
18
+ aMonitor.setFreq(float(aRate));
19
break;
20
}
21
22
23
aMaxRate = stMax(aMaxRate, aRate);
24
}
25
}
26
- aMonitor.setFreqMax(int(aMaxRate));
27
+ aMonitor.setFreqMax(float(aMaxRate));
28
XRRFreeOutputInfo(anOutputInfo);
29
30
XRRFreeCrtcInfo(aCrtcInfo);
31
sview-17_04.tar.gz/StCore/StWinHandles.cpp -> sview-20_08.tar.gz/StCore/StWinHandles.cpp
Changed
76
1
2
#define ST_EGL_CONTEXT_OPENGL_CORE_PROFILE_BIT_KHR 0x00000001
3
#define ST_EGL_CONTEXT_OPENGL_COMPATIBILITY_PROFILE_BIT_KHR 0x00000002
4
5
+ // for EGL_KHR_context_flush_control
6
+ #define ST_EGL_CONTEXT_RELEASE_BEHAVIOR_KHR 0x2097
7
+ #define ST_EGL_CONTEXT_RELEASE_BEHAVIOR_NONE_KHR 0x0000
8
+ #define ST_EGL_CONTEXT_RELEASE_BEHAVIOR_FLUSH_KHR 0x2098
9
+
10
const char* anEglExts = eglQueryString(myDisplay, EGL_EXTENSIONS);
11
if(StGLContext::stglCheckExtension(anEglExts, "EGL_KHR_create_context")) {
12
+ const bool khrFlushControl = StGLContext::stglCheckExtension(anEglExts, "EGL_KHR_context_flush_control");
13
const EGLint anEglCtxAttribs[] = {
14
ST_EGL_CONTEXT_FLAGS_KHR, theDebugCtx ? ST_EGL_CONTEXT_OPENGL_DEBUG_BIT_KHR : 0,
15
#if defined(GL_ES_VERSION_2_0)
16
EGL_CONTEXT_CLIENT_VERSION, 2,
17
#endif
18
//EGL_CONTEXT_OPENGL_PROFILE_MASK_KHR, ST_EGL_CONTEXT_OPENGL_COMPATIBILITY_PROFILE_BIT_KHR,
19
+ khrFlushControl ? ST_EGL_CONTEXT_RELEASE_BEHAVIOR_KHR : 0, khrFlushControl ? ST_EGL_CONTEXT_RELEASE_BEHAVIOR_NONE_KHR : 0,
20
EGL_NONE
21
};
22
23
24
25
#else
26
27
+ // GLX_ARB_create_context
28
+#ifndef GLX_CONTEXT_MAJOR_VERSION_ARB
29
+ #define GLX_CONTEXT_DEBUG_BIT_ARB 0x00000001
30
+ #define GLX_CONTEXT_FORWARD_COMPATIBLE_BIT_ARB 0x00000002
31
+ #define GLX_CONTEXT_MAJOR_VERSION_ARB 0x2091
32
+ #define GLX_CONTEXT_MINOR_VERSION_ARB 0x2092
33
+ #define GLX_CONTEXT_FLAGS_ARB 0x2094
34
+
35
+ // GLX_ARB_create_context_profile
36
+ #define GLX_CONTEXT_CORE_PROFILE_BIT_ARB 0x00000001
37
+ #define GLX_CONTEXT_COMPATIBILITY_PROFILE_BIT_ARB 0x00000002
38
+ #define GLX_CONTEXT_PROFILE_MASK_ARB 0x9126
39
+#endif
40
+
41
typedef GLXContext (*glXCreateContextAttribsARB_t)(Display* , GLXFBConfig , GLXContext , Bool , const int* );
42
43
StWinGlrc::StWinGlrc(StHandle<StXDisplay>& theDisplay,
44
45
myRC(NULL) {
46
const char* aGlxExts = glXQueryExtensionsString(theDisplay->hDisplay, DefaultScreen(theDisplay->hDisplay));
47
if(StGLContext::stglCheckExtension(aGlxExts, "GLX_ARB_create_context_profile")) {
48
+ const bool khrFlushControl = StGLContext::stglCheckExtension(aGlxExts, "GLX_ARB_create_context_profile");
49
glXCreateContextAttribsARB_t aCreateCtxFunc = (glXCreateContextAttribsARB_t )glXGetProcAddress((const GLubyte* )"glXCreateContextAttribsARB");
50
51
int aCtxAttribs[] = {
52
//GLX_CONTEXT_MAJOR_VERSION_ARB, 2,
53
//GLX_CONTEXT_MINOR_VERSION_ARB, 0,
54
- GLX_CONTEXT_FLAGS_ARB, theDebugCtx ? GLX_CONTEXT_DEBUG_BIT_ARB : 0,
55
//GLX_CONTEXT_PROFILE_MASK_ARB, GLX_CONTEXT_COMPATIBILITY_PROFILE_BIT_ARB,
56
+ GLX_CONTEXT_FLAGS_ARB, theDebugCtx ? GLX_CONTEXT_DEBUG_BIT_ARB : 0,
57
+ khrFlushControl ? GLX_CONTEXT_RELEASE_BEHAVIOR_ARB : 0, khrFlushControl ? GLX_CONTEXT_RELEASE_BEHAVIOR_NONE_ARB : 0,
58
None
59
};
60
61
62
if(aCtx.extAll->wglCreateContextAttribsARB != NULL) {
63
// Beware! NVIDIA drivers reject context creation when WGL_CONTEXT_PROFILE_MASK_ARB are specified
64
// but not WGL_CONTEXT_MAJOR_VERSION_ARB/WGL_CONTEXT_MINOR_VERSION_ARB
65
- int aCtxAttribs[] = {
66
+ const int aCtxAttribs[] = {
67
//WGL_CONTEXT_MAJOR_VERSION_ARB, 3,
68
//WGL_CONTEXT_MINOR_VERSION_ARB, 2,
69
//WGL_CONTEXT_PROFILE_MASK_ARB, WGL_CONTEXT_COMPATIBILITY_PROFILE_BIT_ARB, //WGL_CONTEXT_CORE_PROFILE_BIT_ARB,
70
- WGL_CONTEXT_FLAGS_ARB, theDebugCtx ? WGL_CONTEXT_DEBUG_BIT_ARB : 0,
71
+ WGL_CONTEXT_FLAGS_ARB, theDebugCtx ? WGL_CONTEXT_DEBUG_BIT_ARB : 0,
72
+ aCtx.khrFlushControl ? WGL_CONTEXT_RELEASE_BEHAVIOR_ARB : 0, aCtx.khrFlushControl ? WGL_CONTEXT_RELEASE_BEHAVIOR_NONE_ARB : 0,
73
0, 0
74
};
75
76
sview-17_04.tar.gz/StCore/StWinHandles.h -> sview-20_08.tar.gz/StCore/StWinHandles.h
Changed
15
1
2
#include "StCocoaView.h"
3
#include "StCocoaWin.h"
4
#elif defined(__linux__)
5
+ // exclude modern definitions and system-provided glext.h, should be defined before gl.h inclusion
6
+ #ifndef GL_GLEXT_LEGACY
7
+ #define GL_GLEXT_LEGACY
8
+ #endif
9
+ #ifndef GLX_GLXEXT_LEGACY
10
+ #define GLX_GLXEXT_LEGACY
11
+ #endif
12
#include <GL/glx.h>
13
#endif
14
15
sview-17_04.tar.gz/StCore/StWindow.cpp -> sview-20_08.tar.gz/StCore/StWindow.cpp
Changed
28
1
2
return myWin->isStereoOutput();
3
}
4
5
+float StWindow::getMaximumTargetFps() const {
6
+ const StSearchMonitors& aMonitors = myWin->getMonitors();;
7
+ const StRectI_t aRect = myWin->getPlacement();
8
+ StMonitor aMon = aMonitors[aRect.center()];
9
+ return aMon.getFreq() >= 24
10
+ ? aMon.getFreq()
11
+ : 60; // fallback for unknown values
12
+}
13
+
14
double StWindow::getTargetFps() const {
15
return myTargetFps;
16
}
17
18
return StQuaternion<double>();
19
}
20
21
+bool StWindow::getCustomProjection(StRectF_t& , StRectF_t& ) const {
22
+ return false;
23
+}
24
+
25
bool StWindow::toSwapEyesHW() const {
26
return myWin->myToSwapEyesHW;
27
}
28
sview-17_04.tar.gz/StCore/StWindowImpl.cpp -> sview-20_08.tar.gz/StCore/StWindowImpl.cpp
Changed
157
1
2
myIsMouseMoved(false) {
3
stMemZero(&attribs, sizeof(attribs));
4
stMemZero(&signals, sizeof(signals));
5
+ myStEvent .Type = stEvent_None;
6
+ myStEvent2 .Type = stEvent_None;
7
+ myStEventAux.Type = stEvent_None;
8
+ myScrollAcc.reset();
9
attribs.IsNoDecor = false;
10
attribs.IsStereoOutput = false;
11
attribs.IsGlStereo = false;
12
13
myTouches.Time = 0.0;
14
myTouches.clearTouches();
15
16
+ myTap0Touch = StTouch::Empty();
17
myTap1Touch.Type = stEvent_TouchCancel;
18
myTap1Touch.Time = 0.0;
19
myTap1Touch.clearTouches();
20
21
case StWinAttr_ToAlignEven:
22
anIter[1] = (StWinAttr )attribs.ToAlignEven;
23
break;
24
+ case StWinAttr_ExclusiveFullScreen:
25
+ anIter[1] = (StWinAttr)attribs.IsExclusiveFullScr;
26
+ break;
27
default:
28
ST_DEBUG_LOG("UNKNOWN window attribute #" + anIter[0] + " requested");
29
break;
30
31
case StWinAttr_ToAlignEven:
32
attribs.ToAlignEven = (anIter[1] == 1);
33
break;
34
+ case StWinAttr_ExclusiveFullScreen:
35
+ attribs.IsExclusiveFullScr = (anIter[1] == 1);
36
+ break;
37
default:
38
ST_DEBUG_LOG("UNKNOWN window attribute #" + anIter[0] + " requested");
39
break;
40
41
}
42
#elif defined(__ANDROID__)
43
int aFlags = 0;
44
+ bool toWakeLock = false;
45
if(attribs.ToBlockSleepDisplay) {
46
aFlags |= AWINDOW_FLAG_KEEP_SCREEN_ON;
47
myBlockSleep = BlockSleep_DISPLAY;
48
+ } else if(attribs.ToBlockSleepSystem) {
49
+ myBlockSleep = BlockSleep_SYSTEM;
50
+ toWakeLock = true;
51
} else {
52
myBlockSleep = BlockSleep_OFF;
53
}
54
if(myParentWin != NULL) {
55
myParentWin->setWindowFlags(aFlags);
56
+ myParentWin->setWakeLock(myWindowTitle, toWakeLock);
57
}
58
#elif defined(__linux__)
59
if(attribs.ToBlockSleepDisplay) { // || attribs.ToBlockSleepSystem
60
61
CURSORINFO aCursor;
62
aCursor.cbSize = sizeof(aCursor);
63
if(GetCursorInfo(&aCursor) != FALSE) {
64
+ if (attribs.IsFullScreen
65
+ && !attribs.IsExclusiveFullScr
66
+ && myTiledCfg == TiledCfg_Separate
67
+ && myParentWin == NULL) {
68
+ // workaround for non-exclusive fullscreen mode
69
+ aCursor.ptScreenPos.y += 2;
70
+ }
71
+
72
return StPointD_t((double(aCursor.ptScreenPos.x) - double(aWinRect.left())) / double(aWinRect.width()),
73
(double(aCursor.ptScreenPos.y) - double(aWinRect.top())) / double(aWinRect.height()));
74
}
75
76
}
77
if(myNbTouchesMax == 0) {
78
myTouches.Time = aTime;
79
+ myTap0Touch = theTouches.Touches[0];
80
}
81
myNbTouchesMax = stMax(myNbTouchesMax, theTouches.NbTouches);
82
83
84
myTap1Touch = aCopy;
85
myTap1Touch.Type = stEvent_TouchUp;
86
myTap1Touch.Time = aTime;
87
+ StGLVec2 aDelta(myTap0Touch.PointX - aCopy.Touches[0].PointX,
88
+ myTap0Touch.PointY - aCopy.Touches[0].PointY);
89
+ aDelta *= aScale;
90
+ if(aDelta.modulus() <= THE_THRESHOLD_TAP.FromIdle) {
91
+ myStEvent2.Type = stEvent_Gesture1Tap;
92
+ myStEvent2.Gesture.clearGesture();
93
+ myStEvent2.Gesture.Time = aTime;
94
+ myStEvent2.Gesture.Point1X = aCopy.Touches[0].PointX;
95
+ myStEvent2.Gesture.Point1Y = aCopy.Touches[0].PointY;
96
+ signals.onGesture->emit(myStEvent2.Gesture);
97
+ }
98
+ } else {
99
+ myTap1Touch.Type = stEvent_TouchCancel;
100
}
101
} else {
102
myTap1Touch.Type = stEvent_TouchCancel;
103
104
}
105
106
bool toUpdate = false;
107
- if(myTouches .NbTouches == 2
108
- && theTouches.NbTouches == 2) {
109
+ if(myTouches .NbTouches == 1
110
+ && theTouches.NbTouches == 1) {
111
+ StTouch aTFrom = myTouches.Touches[0];
112
+ StTouch aTTo = theTouches.findTouchById(aTFrom.Id);
113
+ if(!aTTo.isDefined()) {
114
+ return;
115
+ }
116
+ myTouches.Touches[0] = aTTo;
117
+ } else if(myTouches .NbTouches == 2
118
+ && theTouches.NbTouches == 2) {
119
StTouch aTFrom[2] = {
120
myTouches.Touches[0],
121
myTouches.Touches[1]
122
123
case stEvent_MouseDown:
124
signals.onMouseDown->emit(anEvent.Button);
125
break;
126
- case stEvent_MouseUp:
127
+ case stEvent_MouseUp: {
128
signals.onMouseUp->emit(anEvent.Button);
129
+ if(anEvent.Button.Button != ST_MOUSE_LEFT) {
130
+ myDoubleClickTimer.stop();
131
+ break;
132
+ }
133
+
134
+ // check double click
135
+ const StRectI_t& aWinRect = attribs.IsFullScreen ? myRectFull : myRectNorm;
136
+ const StPointD_t aNewPnt(anEvent.Button.PointX, anEvent.Button.PointY);
137
+ const StPointD_t aDeltaPx = (myDoubleClickPnt - aNewPnt) * StPointD_t(aWinRect.width(), aWinRect.height());
138
+ if(myDoubleClickTimer.isOn()
139
+ && myDoubleClickTimer.getElapsedTime() < 0.4
140
+ && aDeltaPx.cwiseAbs().maxComp() < 3) {
141
+ myStEvent2.Type = stEvent_Gesture1DoubleTap;
142
+ myStEvent2.Gesture.clearGesture();
143
+ myStEvent2.Gesture.Time = anEvent.Button.Time;
144
+ myStEvent2.Gesture.Point1X = (float )anEvent.Button.PointX;
145
+ myStEvent2.Gesture.Point1Y = (float )anEvent.Button.PointY;
146
+ myDoubleClickTimer.stop();
147
+ signals.onGesture->emit(myStEvent2.Gesture);
148
+ } else {
149
+ myDoubleClickTimer.restart();
150
+ }
151
+ myDoubleClickPnt = aNewPnt;
152
break;
153
+ }
154
case stEvent_TouchDown:
155
case stEvent_TouchUp:
156
case stEvent_TouchMove:
157
sview-17_04.tar.gz/StCore/StWindowImpl.h -> sview-20_08.tar.gz/StCore/StWindowImpl.h
Changed
30
1
2
ST_LOCAL bool wndCreateWindows(); // called from non-main thread
3
ST_LOCAL LRESULT stWndProc(HWND , UINT , WPARAM , LPARAM );
4
#elif defined(__APPLE__)
5
+ ST_DISABLE_DEPRECATION_WARNINGS
6
ST_LOCAL void doCreateWindows(NSOpenGLContext* theGLContextMaster,
7
NSOpenGLContext* theGLContextSlave);
8
+ ST_ENABLE_DEPRECATION_WARNINGS
9
#endif
10
11
public:
12
13
bool myIsPreciseCursor; //!< flag indicating that last mouse cursor position was updated by precise input device
14
StTouchEvent myTouches; //!< current state of touch screen
15
StTouchEvent myTap1Touch; //!< previous tap touch
16
+ StTouch myTap0Touch; //!< started tap
17
int myNbTouchesMax; //!< maximum touches within current sequence
18
StRectI_t myRectNorm; //!< master window coordinates in normal state
19
StRectI_t myRectFull; //!< master window coordinates in fullscreen state
20
21
StEvent myStEvent; //!< temporary event object (to be used in message loop thread)
22
StEvent myStEvent2; //!< temporary event object (to be used in message loop thread)
23
StEvent myStEventAux; //!< extra temporary event object (to be used in StWindow creation thread)
24
+ StScrollEvent myScrollAcc; //!< extra temporary event object accumulating mouse scroll events
25
+ StTimer myDoubleClickTimer; //!< timer for detecting double click
26
+ StPointD_t myDoubleClickPnt; //!< double click point
27
int myAlignDL; //!< extra window shift applied for alignment (left)
28
int myAlignDR; //!< extra window shift applied for alignment (right)
29
int myAlignDT; //!< extra window shift applied for alignment (top)
30
sview-17_04.tar.gz/StCore/StWindowImplAnd.cpp -> sview-20_08.tar.gz/StCore/StWindowImplAnd.cpp
Changed
99
1
2
* Update StWindow position according to native parent position.
3
*/
4
void StWindowImpl::updateChildRect() {
5
- if(!attribs.IsFullScreen && (ANativeWindow* )myParentWin != NULL) {
6
+ if(!attribs.IsFullScreen && myParentWin != NULL) {
7
//myRectNorm.right() = myRectNorm.left() + widthReturn;
8
//myRectNorm.bottom() = myRectNorm.top() + heightReturn;
9
10
11
const float aWinSizeY = aWinRect.height();
12
13
// at least single point is defined
14
- StPointD_t aPos0(double(AMotionEvent_getX(theEvent, 0)) / double(aWinSizeX),
15
- double(AMotionEvent_getY(theEvent, 0)) / double(aWinSizeY));
16
+ StPointD_t aPos0Px(AMotionEvent_getX(theEvent, 0), AMotionEvent_getY(theEvent, 0));
17
+ StPointD_t aPos0(double(aPos0Px.x()) / double(aWinSizeX),
18
+ double(aPos0Px.y()) / double(aWinSizeY));
19
20
myStEvent.Type = stEvent_None;
21
myStEvent.Base.Time = getEventTime(); /// int64_t AMotionEvent_getEventTime(theEvent);
22
23
} else if(anAction == AMOTION_EVENT_ACTION_UP) {
24
myStEvent.Type = stEvent_MouseUp;
25
signals.onMouseUp->emit(myStEvent.Button);
26
+ } else if(anAction == AMOTION_EVENT_ACTION_SCROLL) {
27
+ float aScrollX = AMotionEvent_getAxisValue(theEvent, AMOTION_EVENT_AXIS_HSCROLL, 0);
28
+ float aScrollY = AMotionEvent_getAxisValue(theEvent, AMOTION_EVENT_AXIS_VSCROLL, 0);
29
+ myStEvent.Type = stEvent_Scroll;
30
+ myStEvent.Scroll.init(myStEvent.Base.Time, myMousePt.x(), myMousePt.y(),
31
+ aScrollX, aScrollY, false);
32
+ if((myStEvent.Scroll.Time - myScrollAcc.Time) > 0.1
33
+ || std::abs(aPos0Px.x() - myScrollAcc.PointX) > 10
34
+ || std::abs(aPos0Px.y() - myScrollAcc.PointY) > 10) {
35
+ myScrollAcc.reset();
36
+ }
37
+ myScrollAcc.Time = myStEvent.Scroll.Time;
38
+ myScrollAcc.PointX = aPos0Px.x();
39
+ myScrollAcc.PointY = aPos0Px.y();
40
+ myStEvent.Scroll.StepsX = myScrollAcc.accumulateStepsX(int(aScrollX * 1000.0), 1000);
41
+ myStEvent.Scroll.StepsY = myScrollAcc.accumulateStepsY(int(aScrollY * 1000.0), 1000);
42
+ signals.onScroll->emit(myStEvent.Scroll);
43
}
44
return;
45
}
46
47
48
// check onNewIntent event
49
StString aDndFile;
50
+ myParentWin->setWindowTitle(myWindowTitle);
51
myParentWin->setHardwareStereoOn(myToEnableStereoHW);
52
myParentWin->setTrackOrientation(myToTrackOrient);
53
myParentWin->setHideSystemBars(myToHideStatusBar, myToHideNavBar);
54
- myParentWin->fetchState(aDndFile, myQuaternion, myToSwapEyesHW);
55
+ myParentWin->fetchState(aDndFile, myQuaternion, myToSwapEyesHW, myKeysState);
56
if(!aDndFile.isEmpty()) {
57
- std::vector<const char*> aDndList;
58
- aDndList.push_back(aDndFile.toCString());
59
- myStEvent.Type = stEvent_FileDrop;
60
- myStEvent.DNDrop.Time = getEventTime();
61
- myStEvent.DNDrop.NbFiles = aDndList.size();
62
- myStEvent.DNDrop.Files = &aDndList[0];
63
- myEventsBuffer.append(myStEvent);
64
+ // notice - unpress event will NOT be generated!
65
+ myStEvent.Type = stEvent_KeyDown;
66
+ myStEvent.Key.Time = getEventTime();
67
+ myStEvent.Key.Flags = ST_VF_NONE;
68
+ if(aDndFile == "ACTION_PLAY_PREV") {
69
+ myStEvent.Key.VKey = ST_VK_MEDIA_PREV_TRACK;
70
+ myEventsBuffer.append(myStEvent);
71
+ } else if(aDndFile == "ACTION_PLAY_NEXT") {
72
+ myStEvent.Key.VKey = ST_VK_MEDIA_NEXT_TRACK;
73
+ myEventsBuffer.append(myStEvent);
74
+ } else if(aDndFile == "ACTION_PLAY_PAUSE") {
75
+ myStEvent.Key.VKey = ST_VK_MEDIA_PLAY_PAUSE;
76
+ myEventsBuffer.append(myStEvent);
77
+ } else {
78
+ std::vector<const char*> aDndList;
79
+ aDndList.push_back(aDndFile.toCString());
80
+ myStEvent.Type = stEvent_FileDrop;
81
+ myStEvent.DNDrop.Time = getEventTime();
82
+ myStEvent.DNDrop.NbFiles = aDndList.size();
83
+ myStEvent.DNDrop.Files = &aDndList[0];
84
+ myEventsBuffer.append(myStEvent);
85
+ }
86
}
87
88
updateActiveState();
89
90
}
91
92
myIsMouseMoved = false;
93
- if(myMousePt.x() >= 0.0 && myMousePt.x() <= 1.0 && myMousePt.y() >= 0.0 && myMousePt.y() <= 1.0) {
94
+ if(myIsPreciseCursor
95
+ && myMousePt.x() >= 0.0 && myMousePt.x() <= 1.0 && myMousePt.y() >= 0.0 && myMousePt.y() <= 1.0) {
96
StPointD_t aDspl = myMousePt - anOldMousePt;
97
if(std::abs(aDspl.x()) >= 0.0008 || std::abs(aDspl.y()) >= 0.0008) {
98
myIsMouseMoved = true;
99
sview-17_04.tar.gz/StCore/StWindowImplLin.cpp -> sview-20_08.tar.gz/StCore/StWindowImplLin.cpp
Changed
10
1
2
myStEvent.Scroll.StepsX = 0;
3
myStEvent.Scroll.StepsY = aBtnEvent->button == 4 ? 1 : -1;
4
myStEvent.Scroll.DeltaX = 0.0;
5
- myStEvent.Scroll.DeltaY = 10.0f * myStEvent.Scroll.StepsY;
6
+ myStEvent.Scroll.DeltaY = myStEvent.Scroll.StepsY;
7
myStEvent.Scroll.IsFromMultiTouch = false;
8
signals.onScroll->emit(myStEvent.Scroll);
9
break;
10
sview-17_04.tar.gz/StCore/StWindowImplMac.mm -> sview-20_08.tar.gz/StCore/StWindowImplMac.mm
Changed
11
1
2
StCocoaLocalPool aLocalPool;
3
4
const bool isNoAccel = false;
5
+ST_DISABLE_DEPRECATION_WARNINGS
6
const NSOpenGLPixelFormatAttribute aDummyAttrib = NSOpenGLPFACompliant;
7
+ST_ENABLE_DEPRECATION_WARNINGS
8
NSOpenGLPixelFormatAttribute anAttribs[] = {
9
attribs.IsGlStereo ? NSOpenGLPFAStereo : aDummyAttrib,
10
//NSOpenGLPFAColorSize, 32,
11
sview-17_04.tar.gz/StCore/StWindowImplWin.cpp -> sview-20_08.tar.gz/StCore/StWindowImplWin.cpp
Changed
71
1
2
return 0;
3
}
4
case WM_MOUSEWHEEL: // vertical wheel
5
- //case WM_MOUSEHWHEEL: // horizontal wheel (only Vista+)
6
+ case WM_MOUSEHWHEEL: // horizontal wheel (only Vista+)
7
{
8
const StRectI_t aWinRect = getPlacement();
9
int aMouseXPx = int(short(LOWORD(lParam))) - aWinRect.left();
10
int aMouseYPx = int(short(HIWORD(lParam))) - aWinRect.top();
11
12
- int aZDelta = GET_WHEEL_DELTA_WPARAM(wParam); // / WHEEL_DELTA;
13
- //if(GET_X_LPARAM(lParam) != 0)
14
-
15
- myStEvent.Type = stEvent_Scroll;
16
- myStEvent.Scroll.Time = getEventTime(myEvent.time);
17
- myStEvent.Scroll.PointX = double(aMouseXPx) / double(aWinRect.width());
18
- myStEvent.Scroll.PointY = double(aMouseYPx) / double(aWinRect.height());
19
- myStEvent.Scroll.StepsX = 0;
20
- myStEvent.Scroll.StepsY = (aZDelta > 0) ? 1 : -1;
21
- myStEvent.Scroll.DeltaX = 0.0;
22
- myStEvent.Scroll.DeltaY = 10.0f * myStEvent.Scroll.StepsY;
23
- myStEvent.Scroll.IsFromMultiTouch = false;
24
-
25
+ const bool isVert = (uMsg == WM_MOUSEWHEEL);
26
+ const int aZDelta = GET_WHEEL_DELTA_WPARAM(wParam);
27
+ const float aDeltaSt = float(aZDelta) / float(WHEEL_DELTA);
28
+
29
+ myStEvent.Scroll.init(getEventTime(myEvent.time),
30
+ double(aMouseXPx) / double(aWinRect.width()),
31
+ double(aMouseYPx) / double(aWinRect.height()),
32
+ !isVert ? aDeltaSt : 0.0f,
33
+ isVert ? aDeltaSt : 0.0f,
34
+ false);
35
+ if((myStEvent.Scroll.Time - myScrollAcc.Time) > 0.1
36
+ || std::abs(aMouseXPx - (int)myScrollAcc.PointX) > 10
37
+ || std::abs(aMouseYPx - (int)myScrollAcc.PointY) > 10) {
38
+ myScrollAcc.reset();
39
+ }
40
+ myScrollAcc.Time = myStEvent.Scroll.Time;
41
+ myScrollAcc.PointX = aMouseXPx;
42
+ myScrollAcc.PointY = aMouseYPx;
43
+ myStEvent.Scroll.StepsX = myScrollAcc.accumulateStepsX(!isVert ? aZDelta : 0, WHEEL_DELTA);
44
+ myStEvent.Scroll.StepsY = myScrollAcc.accumulateStepsY( isVert ? aZDelta : 0, WHEEL_DELTA);
45
myEventsBuffer.append(myStEvent);
46
return 0;
47
}
48
49
} else {
50
// resize Master GL-subwindow
51
myTiledCfg = TiledCfg_Separate;
52
- const GLsizei aSizeX = (attribs.IsFullScreen) ? myRectFull.width() : myRectNorm.width();
53
- const GLsizei aSizeY = (attribs.IsFullScreen) ? myRectFull.height() : myRectNorm.height();
54
+ int aTop = 0;
55
+ int aSizeX = (attribs.IsFullScreen) ? myRectFull.width() : myRectNorm.width();
56
+ int aSizeY = (attribs.IsFullScreen) ? myRectFull.height() : myRectNorm.height();
57
+ if (attribs.IsFullScreen
58
+ && !attribs.IsExclusiveFullScr)
59
+ {
60
+ // workaround slow switching into fullscreen mode and back on Windows 10
61
+ // due to OpenGL driver implicitly activating an exclusive GPU usage mode
62
+ aTop -= 2;
63
+ aSizeY += 2;
64
+ }
65
SetWindowPos(myMaster.hWindowGl, HWND_TOP,
66
- 0, 0, aSizeX, aSizeY,
67
+ 0, aTop, aSizeX, aSizeY,
68
SWP_NOACTIVATE);
69
}
70
}
71
sview-17_04.tar.gz/StCore/StXDisplay.h -> sview-20_08.tar.gz/StCore/StXDisplay.h
Changed
16
1
2
#include <X11/Xlib.h>
3
#include <X11/Xatom.h>
4
#include <X11/Xutil.h>
5
+
6
+// exclude modern definitions and system-provided glext.h, should be defined before gl.h inclusion
7
+#ifndef GL_GLEXT_LEGACY
8
+ #define GL_GLEXT_LEGACY
9
+#endif
10
+#ifndef GLX_GLXEXT_LEGACY
11
+ #define GLX_GLXEXT_LEGACY
12
+#endif
13
#include <GL/glx.h>
14
15
#include <StStrings/StString.h>
16
sview-17_04.tar.gz/StCore/stvkeysxarray.h -> sview-20_08.tar.gz/StCore/stvkeysxarray.h
Changed
19
1
2
ST_VK_COMMA, // 0x2C = XK_comma
3
ST_VK_OEM_MINUS, // 0x2D = XK_minus
4
ST_VK_PERIOD, // 0x2E = XK_period
5
- 0, // 0x2F
6
+ ST_VK_SLASH, // 0x2F = XK_slash
7
ST_VK_0, // 0x30 = XK_0
8
ST_VK_1, // 0x31 = XK_1
9
ST_VK_2, // 0x32 = XK_2
10
11
ST_VK_BRACKETRIGHT, // 0x5D = XK_bracketright
12
ST_VK_NULL, // 0x5E
13
ST_VK_NULL, // 0x5F
14
- ST_VK_NULL, // 0x60
15
+ ST_VK_TILDE, // 0x60 = XK_grave
16
ST_VK_A, // 0x61 = XK_a
17
ST_VK_B, // 0x62 = XK_b
18
ST_VK_C, // 0x63 = XK_c
19
sview-17_04.tar.gz/StDiagnostics/StDiagnostics.cpp -> sview-20_08.tar.gz/StDiagnostics/StDiagnostics.cpp
Changed
28
1
2
myGUI.nullify();
3
return false;
4
}
5
+
6
+ StRectF_t aFrustL, aFrustR;
7
+ if(myWindow->getCustomProjection(aFrustL, aFrustR)) {
8
+ myGUI->changeCamera()->setCustomProjection(aFrustL, aFrustR);
9
+ } else {
10
+ myGUI->changeCamera()->resetCustomProjection();
11
+ }
12
myGUI->stglResize(myWindow->stglViewport(ST_WIN_MASTER), myWindow->getMargins(), (float )myWindow->stglAspectRatio());
13
14
registerHotKeys();
15
16
return;
17
}
18
19
+ StRectF_t aFrustL, aFrustR;
20
+ if(myWindow->getCustomProjection(aFrustL, aFrustR)) {
21
+ myGUI->changeCamera()->setCustomProjection(aFrustL, aFrustR);
22
+ } else {
23
+ myGUI->changeCamera()->resetCustomProjection();
24
+ }
25
myGUI->stglResize(myWindow->stglViewport(ST_WIN_MASTER), myWindow->getMargins(), (float )myWindow->stglAspectRatio());
26
}
27
28
sview-17_04.tar.gz/StDiagnostics/StDiagnostics.rc -> sview-20_08.tar.gz/StDiagnostics/StDiagnostics.rc
Changed
10
1
2
BEGIN
3
VALUE "FileDescription", "Stereoscopic Device Diagnostics\000"
4
VALUE "FileVersion", SVIEW_SDK_VER_STRING "\000"
5
- VALUE "LegalCopyright", "\251 2010-2017 Kirill Gavrilov\000"
6
+ VALUE "LegalCopyright", "\251 2010-2020 Kirill Gavrilov and sView developers\000"
7
VALUE "ProductName", "StDiagnostics\000"
8
VALUE "ProductVersion", SVIEW_SDK_VER_STRING "\000"
9
VALUE "OfficialSite", "www.sview.ru\000"
10
sview-20_08.tar.gz/StDiagnostics/lang/spanish
Added
2
1
+(directory)
2
sview-20_08.tar.gz/StDiagnostics/lang/spanish/StDiagnostics.lng
Added
5
1
2
+# Spanish translation file for StDiagnostics plugin
3
+# @author Kirill Gavrilov
4
+--------
5
sview-17_04.tar.gz/StGLWidgets/StGLCombobox.cpp -> sview-20_08.tar.gz/StGLWidgets/StGLCombobox.cpp
Changed
58
1
2
/**
3
* StGLWidgets, small C++ toolkit for writing GUI using OpenGL.
4
- * Copyright © 2015 Kirill Gavrilov <kirill@sview.ru
5
+ * Copyright © 2015-2020 Kirill Gavrilov <kirill@sview.ru
6
*
7
* Distributed under the Boost Software License, Version 1.0.
8
* See accompanying file license-boost.txt or copy at
9
10
11
#include <StGLWidgets/StGLMenuItem.h>
12
#include <StGLWidgets/StGLMessageBox.h>
13
+#include <StGLWidgets/StGLScrollArea.h>
14
#include <StGLWidgets/StGLRootWidget.h>
15
16
/**
17
18
const int aHeight = myRoot->getRootFullSizeY();
19
changeRectPx().right() = aWidth;
20
changeRectPx().bottom() = aHeight;
21
- create(StString(), StString(), aWidth, aHeight);
22
+ create(StString(), StString(), aWidth, aHeight, false);
23
}
24
25
};
26
27
StGLWidget* aMenuParent = aRoot;
28
if(aRoot->isMobile()) {
29
myBack = new StGLContextBackground(aRoot);
30
- aMenuParent = myBack;
31
+ aMenuParent = myBack->getContent();
32
}
33
34
int aLeft = 0;
35
36
}
37
38
void StGLCombobox::ListBuilder::display() {
39
+ StGLRootWidget* aRoot = myMenu->getRoot();
40
+ const int aRootX = aRoot->getRectPx().width();
41
+ const int aRootY = aRoot->getRectPx().height();
42
if(myBack != NULL) {
43
myBack->stglInit();
44
+ if(myBack->getContent()->isScrollable()) {
45
+ myMenu->setCorner(StGLCorner(ST_VCORNER_TOP, ST_HCORNER_CENTER));
46
+ myMenu->stglResize();
47
+ }
48
} else {
49
- StGLRootWidget* aRoot = myMenu->getRoot();
50
myMenu->stglUpdateSubmenuLayout();
51
- StRectI_t aRect = myMenu->getRectPxAbsolute();
52
- const int aRootX = aRoot->getRectPx().width();
53
- const int aRootY = aRoot->getRectPx().height();
54
+ StRectI_t aRect = myMenu->getRectPxAbsolute();
55
if(aRect.width() >= aRootX) {
56
myMenu->changeRectPx().moveLeftTo(0);
57
} else if(aRect.right() > aRoot->getRectPx().right()) {
58
sview-17_04.tar.gz/StGLWidgets/StGLImageProgram.cpp -> sview-20_08.tar.gz/StGLWidgets/StGLImageProgram.cpp
Changed
541
1
2
/**
3
* StGLWidgets, small C++ toolkit for writing GUI using OpenGL.
4
- * Copyright © 2010-2017 Kirill Gavrilov <kirill@sview.ru>
5
+ * Copyright © 2010-2019 Kirill Gavrilov <kirill@sview.ru>
6
*
7
* Distributed under the Boost Software License, Version 1.0.
8
* See accompanying file license-boost.txt or copy at
9
10
#include <StFile/StRawFile.h>
11
12
namespace {
13
- const char F_DEF_2D[] =
14
+ const char F_DEF_2D_ALPHA[] =
15
"#define stSampler sampler2D\n"
16
- "#define stTexture(theSampler, theCoords) texture2D(theSampler, theCoords.xy)\n";
17
- const char F_DEF_CUBEMAP[] =
18
+ "#define stTexture(theSampler, theCoords) texture2D(theSampler, theCoords.xy)\n"
19
+ "#define stAlpha a\n";
20
+ const char F_DEF_2D_RED[] =
21
+ "#define stSampler sampler2D\n"
22
+ "#define stTexture(theSampler, theCoords) texture2D(theSampler, theCoords.xy)\n"
23
+ "#define stAlpha r\n";
24
+ const char F_DEF_CUBEMAP_ALPHA[] =
25
+ "#define stSampler samplerCube\n"
26
+ "#define stTexture(theSampler, theCoords) textureCube(theSampler, theCoords)\n"
27
+ "#define stAlpha a\n";
28
+ const char F_DEF_CUBEMAP_RED[] =
29
"#define stSampler samplerCube\n"
30
- "#define stTexture(theSampler, theCoords) textureCube(theSampler, theCoords)\n";
31
+ "#define stTexture(theSampler, theCoords) textureCube(theSampler, theCoords)\n"
32
+ "#define stAlpha r\n";
33
}
34
35
-void StGLImageProgram::regToRgb(const int thePartIndex,
36
+void StGLImageProgram::regToRgb(const StGLContext& theCtx,
37
+ const int thePartIndex,
38
const StString& theText) {
39
registerFragmentShaderPart(FragSection_ToRgb, thePartIndex,
40
- StString(F_DEF_2D) + theText);
41
+ StString(theCtx.arbTexRG ? F_DEF_2D_RED : F_DEF_2D_ALPHA) + theText);
42
registerFragmentShaderPart(FragSection_ToRgb, FragToRgb_CUBEMAP + thePartIndex,
43
- StString(F_DEF_CUBEMAP) + theText);
44
+ StString(theCtx.arbTexRG ? F_DEF_CUBEMAP_RED : F_DEF_CUBEMAP_ALPHA) + theText);
45
}
46
47
StGLImageProgram::StGLImageProgram()
48
-: myColorScale(1.0f, 1.0f, 1.0f) {
49
+: myColorScale(1.0f, 1.0f, 1.0f),
50
+ myIsRegistered(false) {
51
myTitle = "StGLImageProgram";
52
53
+ params.gamma = new StFloat32Param(1.0f);
54
+ params.gamma->setMinMaxValues(0.05f, 99.0f);
55
+ params.gamma->setEffectiveMinMaxValues(0.05f, 2.0f);
56
+ params.gamma->setDefValue(1.0f);
57
+ params.gamma->setStep(0.05f);
58
+ params.gamma->setTolerance(0.0001f);
59
+
60
+ params.brightness = new StFloat32Param(1.0f);
61
+ params.brightness->setMinMaxValues(0.0f, 99.0f);
62
+ params.brightness->setDefValue(1.0f);
63
+ params.brightness->setEffectiveMinMaxValues(0.0f, 5.0f);
64
+ params.brightness->setStep(0.05f);
65
+ params.brightness->setTolerance(0.0001f);
66
+
67
+ params.saturation = new StFloat32Param(1.0f);
68
+ params.saturation->setMinMaxValues(-10.0f, 99.0f);
69
+ params.saturation->setEffectiveMinMaxValues(0.0f, 2.0f);
70
+ params.saturation->setDefValue(1.0f);
71
+ params.saturation->setStep(0.05f);
72
+ params.saturation->setTolerance(0.0001f);
73
+}
74
+
75
+void StGLImageProgram::registerFragments(const StGLContext& theCtx) {
76
+ if(myIsRegistered) {
77
+ return;
78
+ }
79
+ myIsRegistered = true;
80
+
81
const char F_SHADER_GET_COLOR_BLEND[] =
82
"uniform sampler2D uTexture;\n"
83
"uniform vec4 uTexData;\n"
84
85
" color = pow(color, uGamma);\n"
86
"}\n\n");
87
88
+ // equiangular cubemap texture coordinates correction
89
+ registerFragmentShaderPart(FragSection_GetTexCoords, FragTexEAC_Off,
90
+ "vec3 getTexCoords(in vec3 theCoords, in vec4 theClamp) { return theCoords; }\n\n");
91
+ registerFragmentShaderPart(FragSection_GetTexCoords, FragTexEAC_On,
92
+ "#define ST_PI 3.1415926535897932384626433832795\n"
93
+ "vec3 getTexCoords(in vec3 theCoords, in vec4 theClamp) {\n"
94
+ " vec3 aCoords = theCoords;\n"
95
+ " aCoords.x = 4.0 / ST_PI * atan(theCoords.x);\n"
96
+ " aCoords.y = 4.0 / ST_PI * atan(theCoords.y);\n"
97
+ " aCoords.z = 4.0 / ST_PI * atan(theCoords.z);\n"
98
+ "\n"
99
+ " float aClampX = abs(theClamp.x) < 1.0 ? theClamp.w * 2.0 : 0.0;\n"
100
+ " if(theClamp.x >= 0.0) {\n"
101
+ " aCoords.x = -1.0 + theClamp.x * (aCoords.x + 1.0);\n"
102
+ " aCoords.x = clamp(aCoords.x, -1.0 + aClampX, 1.0 * theClamp.x);\n"
103
+ " } else {\n"
104
+ " aCoords.x = 1.0 + theClamp.x * (1.0 - aCoords.x);\n"
105
+ " aCoords.x = clamp(aCoords.x, 1.0 * theClamp.x, 1.0 - aClampX);\n"
106
+ " }\n"
107
+ "\n"
108
+ " float aClampY = abs(theClamp.y) < 1.0 ? theClamp.w * 2.0 : 0.0;\n"
109
+ " if(theClamp.y >= 0.0) {\n"
110
+ " aCoords.y = -1.0 + theClamp.y * (aCoords.y + 1.0);\n"
111
+ " aCoords.y = clamp(aCoords.y, -1.0 + aClampY, 1.0 * theClamp.y);\n"
112
+ " } else {\n"
113
+ " aCoords.y = 1.0 + theClamp.y * (1.0 - aCoords.y);\n"
114
+ " aCoords.y = clamp(aCoords.y, 1.0 * theClamp.y, 1.0 - aClampY);\n"
115
+ " }\n"
116
+ "\n"
117
+ " float aClampZ = abs(theClamp.z) < 1.0 ? theClamp.w * 2.0 : 0.0;\n"
118
+ " if(theClamp.z >= 0.0) {\n"
119
+ " aCoords.z = -1.0 + theClamp.z * (aCoords.z + 1.0);\n"
120
+ " aCoords.z = clamp(aCoords.z, -1.0 + aClampZ, 1.0 * theClamp.z);\n"
121
+ " } else {\n"
122
+ " aCoords.z = 1.0 + theClamp.z * (1.0 - aCoords.z);\n"
123
+ " aCoords.z = clamp(aCoords.z, 1.0 * theClamp.z, 1.0 - aClampZ);\n"
124
+ " }\n"
125
+ " return aCoords;\n"
126
+ "}\n\n");
127
+
128
registerFragmentShaderPart(FragSection_ToRgb, FragToRgb_FromRgb,
129
- "void convertToRGB(inout vec4 color, in vec3 texCoord) {}\n\n");
130
-
131
- registerFragmentShaderPart(FragSection_ToRgb, FragToRgb_FromRgba,
132
- "void convertToRGB(inout vec4 color, in vec3 texCoord) {\n"
133
- " vec4 backColor;\n"
134
- " bool evenX = int(mod(floor(gl_FragCoord.x + 1.5), 16.0)) >= 8;\n" // just simple 8 pixels check-board
135
- " bool evenY = int(mod(floor(gl_FragCoord.y + 1.5), 16.0)) >= 8;\n"
136
- " if((evenX && evenY) || (!evenX && !evenY)) {\n"
137
- " backColor = vec4(0.4, 0.4, 0.4, 1.0);\n"
138
- " } else {\n"
139
- " backColor = vec4(0.6, 0.6, 0.6, 1.0);\n"
140
- " }\n"
141
- " color = mix(backColor, color, color.a);\n"
142
+ "void convertToRGB(inout vec4 color, in vec3 texCoord, in vec3 texCoordA) {}\n\n");
143
+
144
+ const char F_ALPHA_BACKGROUND[] =
145
+ "void drawAlphaBackground(inout vec4 theColor) {\n"
146
+ " bool anEvenX = int(mod(floor(gl_FragCoord.x + 1.5), 16.0)) >= 8;\n" // just simple 8 pixels check-board
147
+ " bool anEvenY = int(mod(floor(gl_FragCoord.y + 1.5), 16.0)) >= 8;\n"
148
+ " vec4 aBackColor = vec4(0.6, 0.6, 0.6, 1.0);\n"
149
+ " if((anEvenX && anEvenY) || (!anEvenX && !anEvenY)) {\n"
150
+ " aBackColor = vec4(0.4, 0.4, 0.4, 1.0);\n"
151
+ " };\n"
152
+ " theColor = mix(aBackColor, theColor, theColor.a);\n"
153
+ "}\n\n";
154
+
155
+ registerFragmentShaderPart(FragSection_ToRgb, FragToRgb_FromRgba, StString()
156
+ + F_ALPHA_BACKGROUND
157
+ + "void convertToRGB(inout vec4 color, in vec3 texCoord, in vec3 texCoordA) {\n"
158
+ " drawAlphaBackground(color);\n"
159
"}\n\n");
160
- registerFragmentShaderPart(FragSection_ToRgb, FragToRgb_FromGray,
161
- "void convertToRGB(inout vec4 color, in vec3 texCoord) {\n"
162
- " color.r = color.a;\n" // gray scale stored in alpha
163
- " color.g = color.a;\n"
164
- " color.b = color.a;\n"
165
+
166
+ regToRgb(theCtx, FragToRgb_FromGray,
167
+ "void convertToRGB(inout vec4 color, in vec3 texCoord, in vec3 texCoordA) {\n"
168
+ " color.r = color.stAlpha;\n" // gray scale stored in alpha
169
+ " color.g = color.stAlpha;\n"
170
+ " color.b = color.stAlpha;\n"
171
"}\n\n");
172
173
// color conversion shaders
174
175
" 0.0, 0.0, 0.0, 1.0);"
176
"const vec4 THE_GAMMA_XYZ = vec4(2.6, 2.6, 2.6, 1.0);"
177
"const vec4 THE_GAMMA_RGB = 1.0 / vec4(2.2, 2.2, 2.2, 1.0);"
178
- "void convertToRGB(inout vec4 theColor, in vec3 texCoord) {\n"
179
+ "void convertToRGB(inout vec4 theColor, in vec3 texCoord, in vec3 texCoordA) {\n"
180
" vec4 aColor = pow(theColor, THE_GAMMA_XYZ);"
181
" aColor = THE_XYZ2RGB_MAT * aColor;\n"
182
" aColor = pow(aColor, THE_GAMMA_RGB);"
183
184
const char F_SHADER_YUV2RGB_MPEG[] =
185
"uniform stSampler uTextureU;\n"
186
"uniform stSampler uTextureV;\n"
187
- "void convertToRGB(inout vec4 color, in vec3 texCoordUV) {\n"
188
- " vec3 colorYUV = vec3(color.a, stTexture(uTextureU, texCoordUV).a, stTexture(uTextureV, texCoordUV).a);\n"
189
+ "void convertToRGB(inout vec4 color, in vec3 texCoordUV, in vec3 texCoordA) {\n"
190
+ " vec3 colorYUV = vec3(color.stAlpha, stTexture(uTextureU, texCoordUV).stAlpha, stTexture(uTextureV, texCoordUV).stAlpha);\n"
191
+ " colorYUV *= TheRangeBits;\n"
192
+ " colorYUV.x = 1.1643 * (colorYUV.x - 0.0625);\n"
193
+ " colorYUV.y -= 0.5;\n"
194
+ " colorYUV.z -= 0.5;\n"
195
+ " color.r = colorYUV.x + 1.5958 * colorYUV.z;\n"
196
+ " color.g = colorYUV.x - 0.39173 * colorYUV.y - 0.81290 * colorYUV.z;\n"
197
+ " color.b = colorYUV.x + 2.017 * colorYUV.y;\n"
198
+ "}\n\n";
199
+
200
+ const char F_SHADER_YUVA2RGB_MPEG[] =
201
+ "uniform stSampler uTextureU;\n"
202
+ "uniform stSampler uTextureV;\n"
203
+ "uniform stSampler uTextureA;\n"
204
+ "void convertToRGB(inout vec4 color, in vec3 texCoordUV, in vec3 texCoordA) {\n"
205
+ " vec3 colorYUV = vec3(color.stAlpha, stTexture(uTextureU, texCoordUV).stAlpha, stTexture(uTextureV, texCoordUV).stAlpha);\n"
206
" colorYUV *= TheRangeBits;\n"
207
" colorYUV.x = 1.1643 * (colorYUV.x - 0.0625);\n"
208
" colorYUV.y -= 0.5;\n"
209
210
" color.r = colorYUV.x + 1.5958 * colorYUV.z;\n"
211
" color.g = colorYUV.x - 0.39173 * colorYUV.y - 0.81290 * colorYUV.z;\n"
212
" color.b = colorYUV.x + 2.017 * colorYUV.y;\n"
213
+ " color.a = stTexture(uTextureA, texCoordA).stAlpha;\n" // TODO how to handle TheRangeBits?
214
+ " drawAlphaBackground(color);\n"
215
"}\n\n";
216
217
const char F_SHADER_YUV2RGB_FULL[] =
218
"uniform stSampler uTextureU;\n"
219
"uniform stSampler uTextureV;\n"
220
- "void convertToRGB(inout vec4 color, in vec3 texCoordUV) {\n"
221
- " vec3 colorYUV = vec3(color.a, stTexture(uTextureU, texCoordUV).a, stTexture(uTextureV, texCoordUV).a);\n"
222
+ "void convertToRGB(inout vec4 color, in vec3 texCoordUV, in vec3 texCoordA) {\n"
223
+ " vec3 colorYUV = vec3(color.stAlpha, stTexture(uTextureU, texCoordUV).stAlpha, stTexture(uTextureV, texCoordUV).stAlpha);\n"
224
" colorYUV *= TheRangeBits;\n"
225
" colorYUV.x = colorYUV.x;\n"
226
" colorYUV.y -= 0.5;\n"
227
228
" color.b = colorYUV.x + 1.772 * colorYUV.y;\n"
229
"}\n\n";
230
231
+ const char F_SHADER_YUVA2RGB_FULL[] =
232
+ "uniform stSampler uTextureU;\n"
233
+ "uniform stSampler uTextureV;\n"
234
+ "uniform stSampler uTextureA;\n"
235
+ "void convertToRGB(inout vec4 color, in vec3 texCoordUV, in vec3 texCoordA) {\n"
236
+ " vec3 colorYUV = vec3(color.stAlpha, stTexture(uTextureU, texCoordUV).stAlpha, stTexture(uTextureV, texCoordUV).stAlpha);\n"
237
+ " colorYUV *= TheRangeBits;\n"
238
+ " colorYUV.x = colorYUV.x;\n"
239
+ " colorYUV.y -= 0.5;\n"
240
+ " colorYUV.z -= 0.5;\n"
241
+ " color.r = colorYUV.x + 1.402 * colorYUV.z;\n"
242
+ " color.g = colorYUV.x - 0.344 * colorYUV.y - 0.714 * colorYUV.z;\n"
243
+ " color.b = colorYUV.x + 1.772 * colorYUV.y;\n"
244
+ " color.a = stTexture(uTextureA, texCoordA).stAlpha;\n" // TODO how to handle TheRangeBits?
245
+ " drawAlphaBackground(color);\n"
246
+ "}\n\n";
247
+
248
const char F_SHADER_YUVNV2RGB_MPEG[] =
249
"uniform stSampler uTextureU;\n"
250
- "void convertToRGB(inout vec4 color, in vec3 texCoordUV) {\n"
251
- " vec3 colorYUV = vec3(color.a, stTexture(uTextureU, texCoordUV).r, stTexture(uTextureU, texCoordUV).a);\n"
252
+ "void convertToRGB(inout vec4 color, in vec3 texCoordUV, in vec3 texCoordA) {\n"
253
+ " vec3 colorYUV = vec3(color.stAlpha, stTexture(uTextureU, texCoordUV).r, stTexture(uTextureU, texCoordUV).a);\n"
254
" colorYUV *= TheRangeBits;\n"
255
" colorYUV.x = 1.1643 * (colorYUV.x - 0.0625);\n"
256
" colorYUV.y -= 0.5;\n"
257
258
259
const char F_SHADER_YUVNV2RGB_FULL[] =
260
"uniform stSampler uTextureU;\n"
261
- "void convertToRGB(inout vec4 color, in vec3 texCoordUV) {\n"
262
- " vec3 colorYUV = vec3(color.a, stTexture(uTextureU, texCoordUV).r, stTexture(uTextureU, texCoordUV).a);\n"
263
+ "void convertToRGB(inout vec4 color, in vec3 texCoordUV, in vec3 texCoordA) {\n"
264
+ " vec3 colorYUV = vec3(color.stAlpha, stTexture(uTextureU, texCoordUV).r, stTexture(uTextureU, texCoordUV).a);\n"
265
" colorYUV *= TheRangeBits;\n"
266
" colorYUV.x = colorYUV.x;\n"
267
" colorYUV.y -= 0.5;\n"
268
269
" color.b = colorYUV.x + 1.772 * colorYUV.y;\n"
270
"}\n\n";
271
272
- regToRgb(FragToRgb_FromYuvFull, StString()
273
+ regToRgb(theCtx, FragToRgb_FromYuvFull, StString()
274
+ "const float TheRangeBits = 1.0;\n"
275
+ F_SHADER_YUV2RGB_FULL);
276
277
- regToRgb(FragToRgb_FromYuvMpeg, StString()
278
+ regToRgb(theCtx, FragToRgb_FromYuvaFull, StString()
279
+ + "const float TheRangeBits = 1.0;\n"
280
+ + F_ALPHA_BACKGROUND
281
+ + F_SHADER_YUVA2RGB_FULL);
282
+
283
+ regToRgb(theCtx, FragToRgb_FromYuvMpeg, StString()
284
+ "const float TheRangeBits = 1.0;\n"
285
+ F_SHADER_YUV2RGB_MPEG);
286
287
- regToRgb(FragToRgb_FromYuv9Full, StString()
288
+ regToRgb(theCtx, FragToRgb_FromYuvaMpeg, StString()
289
+ + "const float TheRangeBits = 1.0;\n"
290
+ + F_ALPHA_BACKGROUND
291
+ + F_SHADER_YUVA2RGB_MPEG);
292
+
293
+ regToRgb(theCtx, FragToRgb_FromYuv9Full, StString()
294
+ "const float TheRangeBits = 65535.0 / 511.0;\n"
295
+ F_SHADER_YUV2RGB_FULL);
296
297
- regToRgb(FragToRgb_FromYuv9Mpeg, StString()
298
+ regToRgb(theCtx, FragToRgb_FromYuva9Full, StString()
299
+ + "const float TheRangeBits = 65535.0 / 511.0;\n"
300
+ + F_ALPHA_BACKGROUND
301
+ + F_SHADER_YUVA2RGB_FULL);
302
+
303
+ regToRgb(theCtx, FragToRgb_FromYuv9Mpeg, StString()
304
+ "const float TheRangeBits = 65535.0 / 511.0;\n"
305
+ F_SHADER_YUV2RGB_MPEG);
306
307
- regToRgb(FragToRgb_FromYuv10Full, StString()
308
+ regToRgb(theCtx, FragToRgb_FromYuva9Mpeg, StString()
309
+ + "const float TheRangeBits = 65535.0 / 511.0;\n"
310
+ + F_ALPHA_BACKGROUND
311
+ + F_SHADER_YUVA2RGB_MPEG);
312
+
313
+ regToRgb(theCtx, FragToRgb_FromYuv10Full, StString()
314
+ "const float TheRangeBits = 65535.0 / 1023.0;\n"
315
+ F_SHADER_YUV2RGB_FULL);
316
317
- regToRgb(FragToRgb_FromYuv10Mpeg, StString()
318
+ regToRgb(theCtx, FragToRgb_FromYuva10Full, StString()
319
+ + "const float TheRangeBits = 65535.0 / 1023.0;\n"
320
+ + F_ALPHA_BACKGROUND
321
+ + F_SHADER_YUVA2RGB_FULL);
322
+
323
+ regToRgb(theCtx, FragToRgb_FromYuv10Mpeg, StString()
324
+ "const float TheRangeBits = 65535.0 / 1023.0;\n"
325
+ F_SHADER_YUV2RGB_MPEG);
326
327
- regToRgb(FragToRgb_FromYuvNvFull, StString()
328
+ regToRgb(theCtx, FragToRgb_FromYuva10Mpeg, StString()
329
+ + "const float TheRangeBits = 65535.0 / 1023.0;\n"
330
+ + F_ALPHA_BACKGROUND
331
+ + F_SHADER_YUVA2RGB_MPEG);
332
+
333
+ regToRgb(theCtx, FragToRgb_FromYuvNvFull, StString()
334
+ "const float TheRangeBits = 1.0;\n"
335
+ F_SHADER_YUVNV2RGB_FULL);
336
337
- regToRgb(FragToRgb_FromYuvNvMpeg, StString()
338
+ regToRgb(theCtx, FragToRgb_FromYuvNvMpeg, StString()
339
+ "const float TheRangeBits = 1.0;\n"
340
+ F_SHADER_YUVNV2RGB_MPEG);
341
342
- params.gamma = new StFloat32Param(1.0f);
343
- params.gamma->setMinMaxValues(0.05f, 99.0f);
344
- params.gamma->setEffectiveMinMaxValues(0.05f, 2.0f);
345
- params.gamma->setDefValue(1.0f);
346
- params.gamma->setStep(0.05f);
347
- params.gamma->setTolerance(0.0001f);
348
-
349
- params.brightness = new StFloat32Param(1.0f);
350
- params.brightness->setMinMaxValues(0.0f, 99.0f);
351
- params.brightness->setDefValue(1.0f);
352
- params.brightness->setEffectiveMinMaxValues(0.0f, 5.0f);
353
- params.brightness->setStep(0.05f);
354
- params.brightness->setTolerance(0.0001f);
355
-
356
- params.saturation = new StFloat32Param(1.0f);
357
- params.saturation->setMinMaxValues(-10.0f, 99.0f);
358
- params.saturation->setEffectiveMinMaxValues(0.0f, 2.0f);
359
- params.saturation->setDefValue(1.0f);
360
- params.saturation->setStep(0.05f);
361
- params.saturation->setTolerance(0.0001f);
362
-
363
// main shader parts
364
const char V_SHADER_FLAT[] =
365
"uniform mat4 uProjMat;\n"
366
"uniform mat4 uModelMat;\n"
367
"uniform vec4 uTexData;\n"
368
"uniform vec4 uTexUVData;\n"
369
+ "uniform vec4 uTexAData;\n"
370
371
"attribute vec4 vVertex;\n"
372
"attribute vec2 vTexCoord;\n"
373
374
"varying vec3 fTexCoord;\n"
375
"varying vec3 fTexUVCoord;\n"
376
+ "varying vec3 fTexACoord;\n"
377
+ "varying vec3 fTexClamp;\n"
378
+ "varying float fTexClampW;\n"
379
380
"void main(void) {\n"
381
" fTexCoord = vec3(uTexData.xy + vTexCoord * uTexData.zw, 0.0);\n"
382
" fTexUVCoord = vec3(uTexUVData.xy + vTexCoord * uTexUVData.zw, 0.0);\n"
383
+ " fTexACoord = vec3(uTexAData.xy + vTexCoord * uTexAData.zw, 0.0);\n"
384
+ " fTexClamp = vec3(0.0, 0.0, 0.0);\n"
385
+ " fTexClampW = 0.0;\n"
386
" gl_Position = uProjMat * uModelMat * vVertex;\n"
387
"}\n";
388
389
390
"uniform mat4 uModelMat;\n"
391
"uniform vec4 uTexData;\n"
392
"uniform vec4 uTexUVData;\n"
393
+ "uniform vec4 uTexAData;\n"
394
"uniform float uTexCubeFlipZ;\n"
395
396
"attribute vec4 vVertex;\n"
397
- "attribute vec2 vTexCoord;\n"
398
+ "attribute vec3 vNormal;\n"
399
+ "attribute vec4 vColor;\n"
400
401
"varying vec3 fTexCoord;\n"
402
"varying vec3 fTexUVCoord;\n"
403
+ "varying vec3 fTexACoord;\n"
404
+ "varying vec3 fTexClamp;\n"
405
+ "varying float fTexClampW;\n"
406
407
"void main(void) {\n"
408
- " gl_Position = vec4(vVertex.x, vVertex.y, 0.0, 1.0);\n"
409
- " vec3 aTCoord = (uProjMat * gl_Position).xyz;"
410
- " aTCoord.z *= uTexCubeFlipZ;"
411
- " fTexCoord = aTCoord;"
412
- " fTexUVCoord = aTCoord;"
413
+ " vec4 aPos = uProjMat * uModelMat * vec4(vVertex.xyz, 1.0);\n"
414
+ " gl_Position = aPos.xyww;\n"
415
+ " vec3 aTCoord = vNormal;\n" // fake normal attribute
416
+ " aTCoord.z *= uTexCubeFlipZ;\n"
417
+ " fTexCoord = aTCoord;\n"
418
+ " fTexUVCoord = aTCoord;\n"
419
+ " fTexACoord = aTCoord;\n"
420
+ " fTexClamp = vColor.xyz;\n" // fake color attribute
421
+ " fTexClampW = vColor.w;\n"
422
"}\n";
423
424
const char F_SHADER_FLAT[] =
425
"varying vec3 fTexCoord;\n"
426
"varying vec3 fTexUVCoord;\n"
427
+ "varying vec3 fTexACoord;\n"
428
+ "varying vec3 fTexClamp;\n"
429
+ "varying float fTexClampW;\n"
430
// we split these functions for two reasons:
431
// - to change function code (like color conversion);
432
// - to optimize rendering on old hardware not supported conditions (GeForce FX for example).
433
+ "vec3 getTexCoords(in vec3 theCoords, in vec4 theClamp);\n"
434
"vec4 getColor(in vec3 texCoord);\n"
435
- "void convertToRGB(inout vec4 theColor, in vec3 theTexUVCoord);\n"
436
+ "void convertToRGB(inout vec4 theColor, in vec3 theTexUVCoord, in vec3 texCoordA);\n"
437
"void applyCorrection(inout vec4 theColor);\n"
438
"void applyGamma(inout vec4 theColor);\n"
439
440
"void main(void) {\n"
441
+ " vec4 aTexClamp = vec4(fTexClamp, fTexClampW);\n"
442
+ " vec3 aTexCoord = getTexCoords(fTexCoord, aTexClamp);\n"
443
+ " vec3 aTexCoordUV = getTexCoords(fTexUVCoord, aTexClamp);\n"
444
+ " vec3 aTexCoordA = getTexCoords(fTexACoord, aTexClamp);\n"
445
// extract color from main texture
446
- " vec4 aColor = getColor(fTexCoord);\n"
447
+ " vec4 aColor = getColor(aTexCoord);\n"
448
// convert from alien color model (like YUV) to RGB
449
- " convertToRGB(aColor, fTexUVCoord);\n"
450
+ " convertToRGB(aColor, aTexCoordUV, aTexCoordA);\n"
451
// color processing (saturation, brightness, etc)
452
" applyCorrection(aColor);\n"
453
// gamma correction
454
455
theCtx.core20fwd->glUniform4fv(uniTexUVDataLoc, 1, theTexDataVec4);
456
}
457
458
+void StGLImageProgram::setTextureADataSize(StGLContext& theCtx,
459
+ const StGLVec4& theTexDataVec4) {
460
+ theCtx.core20fwd->glUniform4fv(uniTexADataLoc, 1, theTexDataVec4);
461
+}
462
+
463
void StGLImageProgram::setCubeTextureFlipZ(StGLContext& theCtx,
464
bool theToFlip) {
465
theCtx.core20fwd->glUniform1f(uniTexCubeFlipZLoc, theToFlip ? 1.0f : -1.0f);
466
467
case StImage::ImgColor_RGBA: return StGLImageProgram::FragToRgb_FromRgba;
468
case StImage::ImgColor_GRAY: return StGLImageProgram::FragToRgb_FromGray;
469
case StImage::ImgColor_XYZ: return StGLImageProgram::FragToRgb_FromXyz;
470
- case StImage::ImgColor_YUV: {
471
+ case StImage::ImgColor_YUV:
472
+ case StImage::ImgColor_YUVA: {
473
+ const bool hasAlpha = theColorModel == StImage::ImgColor_YUVA;
474
switch(theColorScale) {
475
- case StImage::ImgScale_Mpeg9: return StGLImageProgram::FragToRgb_FromYuv9Mpeg;
476
- case StImage::ImgScale_Mpeg10: return StGLImageProgram::FragToRgb_FromYuv10Mpeg;
477
- case StImage::ImgScale_Jpeg9: return StGLImageProgram::FragToRgb_FromYuv9Full;
478
- case StImage::ImgScale_Jpeg10: return StGLImageProgram::FragToRgb_FromYuv10Full;
479
- case StImage::ImgScale_Mpeg: return StGLImageProgram::FragToRgb_FromYuvMpeg;
480
- case StImage::ImgScale_Full: return StGLImageProgram::FragToRgb_FromYuvFull;
481
+ case StImage::ImgScale_Mpeg9: return hasAlpha ? StGLImageProgram::FragToRgb_FromYuva9Mpeg : StGLImageProgram::FragToRgb_FromYuv9Mpeg;
482
+ case StImage::ImgScale_Mpeg10: return hasAlpha ? StGLImageProgram::FragToRgb_FromYuva10Mpeg : StGLImageProgram::FragToRgb_FromYuv10Mpeg;
483
+ case StImage::ImgScale_Jpeg9: return hasAlpha ? StGLImageProgram::FragToRgb_FromYuva9Full : StGLImageProgram::FragToRgb_FromYuv9Full;
484
+ case StImage::ImgScale_Jpeg10: return hasAlpha ? StGLImageProgram::FragToRgb_FromYuva10Full : StGLImageProgram::FragToRgb_FromYuv10Full;
485
+ case StImage::ImgScale_Mpeg: return hasAlpha ? StGLImageProgram::FragToRgb_FromYuvaMpeg : StGLImageProgram::FragToRgb_FromYuvMpeg;
486
+ case StImage::ImgScale_Full: return hasAlpha ? StGLImageProgram::FragToRgb_FromYuvaFull : StGLImageProgram::FragToRgb_FromYuvFull;
487
case StImage::ImgScale_NvMpeg: return StGLImageProgram::FragToRgb_FromYuvNvMpeg;
488
case StImage::ImgScale_NvFull: return StGLImageProgram::FragToRgb_FromYuvNvFull;
489
}
490
- return StGLImageProgram::FragToRgb_FromYuvFull;
491
+ return hasAlpha ? StGLImageProgram::FragToRgb_FromYuvaFull : StGLImageProgram::FragToRgb_FromYuvFull;
492
}
493
default: {
494
ST_DEBUG_LOG("No GLSL shader for this color model = " + theColorModel);
495
496
bool StGLImageProgram::init(StGLContext& theCtx,
497
const StImage::ImgColorModel theColorModel,
498
const StImage::ImgColorScale theColorScale,
499
- const FragGetColor theFilter) {
500
+ const FragGetColor theFilter,
501
+ const FragTexEAC theTexCoord) {
502
+ registerFragments(theCtx);
503
504
// re-configure shader parts when required
505
bool isChanged = myActiveProgram.isNull();
506
507
}
508
509
isChanged = setFragmentShaderPart(theCtx, FragSection_ToRgb, aToRgb) || isChanged;
510
+ isChanged = setFragmentShaderPart(theCtx, FragSection_GetTexCoords, theTexCoord) || isChanged;
511
isChanged = setFragmentShaderPart(theCtx, FragSection_GetColor, theFilter) || isChanged;
512
isChanged = setVertexShaderPart (theCtx, 0, theFilter == FragGetColor_Cubemap ? VertMain_Cubemap : VertMain_Normal) || isChanged;
513
if(isChanged) {
514
515
myActiveProgram->uniModelMatLoc = myActiveProgram->getUniformLocation(theCtx, "uModelMat");
516
uniTexMainDataLoc = myActiveProgram->getUniformLocation(theCtx, "uTexData");
517
uniTexUVDataLoc = myActiveProgram->getUniformLocation(theCtx, "uTexUVData");
518
+ uniTexADataLoc = myActiveProgram->getUniformLocation(theCtx, "uTexAData");
519
uniTexSizePxLoc = myActiveProgram->getUniformLocation(theCtx, "uTexSizePx");
520
uniTexelSizePxLoc = myActiveProgram->getUniformLocation(theCtx, "uTexelSize");
521
uniTexCubeFlipZLoc = myActiveProgram->getUniformLocation(theCtx, "uTexCubeFlipZ");
522
523
uniGammaLoc = myActiveProgram->getUniformLocation(theCtx, "uGamma");
524
myActiveProgram->atrVVertexLoc = myActiveProgram->getAttribLocation(theCtx, "vVertex");
525
myActiveProgram->atrVTCoordLoc = myActiveProgram->getAttribLocation(theCtx, "vTexCoord");
526
+ myActiveProgram->atrVNormalLoc = myActiveProgram->getAttribLocation(theCtx, "vNormal");
527
+ myActiveProgram->atrVColorsLoc = myActiveProgram->getAttribLocation(theCtx, "vColor");
528
529
StGLVarLocation uniTextureLoc = myActiveProgram->getUniformLocation(theCtx, "uTexture");
530
StGLVarLocation uniTextureULoc = myActiveProgram->getUniformLocation(theCtx, "uTextureU");
531
StGLVarLocation uniTextureVLoc = myActiveProgram->getUniformLocation(theCtx, "uTextureV");
532
+ StGLVarLocation uniTextureALoc = myActiveProgram->getUniformLocation(theCtx, "uTextureA");
533
myActiveProgram->use(theCtx);
534
theCtx.core20fwd->glUniform1i(uniTextureLoc, StGLProgram::TEXTURE_SAMPLE_0);
535
theCtx.core20fwd->glUniform1i(uniTextureULoc, StGLProgram::TEXTURE_SAMPLE_1);
536
theCtx.core20fwd->glUniform1i(uniTextureVLoc, StGLProgram::TEXTURE_SAMPLE_2);
537
+ theCtx.core20fwd->glUniform1i(uniTextureALoc, StGLProgram::TEXTURE_SAMPLE_3);
538
myActiveProgram->unuse(theCtx);
539
540
/*if (!uniModelMatLoc.isValid()
541
sview-17_04.tar.gz/StGLWidgets/StGLImageRegion.cpp -> sview-20_08.tar.gz/StGLWidgets/StGLImageRegion.cpp
Changed
942
1
2
/**
3
* StGLWidgets, small C++ toolkit for writing GUI using OpenGL.
4
- * Copyright © 2010-2016 Kirill Gavrilov <kirill@sview.ru>
5
+ * Copyright © 2010-2020 Kirill Gavrilov <kirill@sview.ru>
6
*
7
* Distributed under the Boost Software License, Version 1.0.
8
* See accompanying file license-boost.txt or copy at
9
10
11
#include <StGLWidgets/StGLImageRegion.h>
12
#include <StGLWidgets/StGLRootWidget.h>
13
+#include <StGLWidgets/StGLTextureButton.h>
14
#include <StGL/StPlayList.h>
15
#include <StGLStereo/StGLQuadTexture.h>
16
17
18
19
// we use negative scale factor to show sphere inside out!
20
static const float THE_SPHERE_RADIUS = -10.0f;
21
- static const float THE_PANORAMA_DEF_ZOOM = 0.45f;
22
+ static const float THE_PANORAMA_DEF_ZOOM = 0.45f; // circa 85 degrees FOV
23
24
+ static const float THE_THEATER_ANGLE = float(M_PI * 0.5);
25
+ static const float THE_THEATER_FROM = float(M_PI) - THE_THEATER_ANGLE * 0.5f;
26
}
27
28
StGLImageRegion::StGLImageRegion(StGLWidget* theParent,
29
const StHandle<StGLTextureQueue>& theTextureQueue,
30
bool theUsePanningKeys)
31
: StGLWidget(theParent, 0, 0, StGLCorner(ST_VCORNER_TOP, ST_HCORNER_LEFT)),
32
- myQuad(),
33
- myUVSphere(StGLVec3(0.0f, 0.0f, 0.0f), 1.0f, 64),
34
+ myIconPrev(NULL),
35
+ myIconNext(NULL),
36
+ myCube(GL_TRIANGLES),
37
+ myCubePano(StPanorama_OFF),
38
+ myUVSphere (StGLVec3(0.0f, 0.0f, 0.0f), 1.0f, 64, false),
39
+ myHemisphere(StGLVec3(0.0f, 0.0f, 0.0f), 1.0f, 64, true),
40
+ myCylinder (StGLVec3(0.0f, 0.0f, 0.0f), 1.0f, 1.0f, 64),
41
+ myTheater (StGLVec3(0.0f, 0.0f, 0.0f), 1.0f, 1.0f, THE_THEATER_FROM, THE_THEATER_FROM + THE_THEATER_ANGLE, 64),
42
myTextureQueue(theTextureQueue),
43
myClickPntZo(0.0, 0.0),
44
myKeyFlags(ST_VF_NONE),
45
myDragDelayMs(0.0),
46
+ myDragDelayTmpMs(0.0),
47
+ mySampleRatio(1.0f),
48
myRotAngle(0.0f),
49
myIsClickAborted(false),
50
#ifdef ST_EXTRA_CONTROLS
51
52
#endif
53
myIsInitialized(false),
54
myHasVideoStream(false) {
55
+ myIconPrev = new StGLIcon(this, getRoot()->scale(48), 0, StGLCorner(ST_VCORNER_CENTER, ST_HCORNER_LEFT), 1);
56
+ myIconPrev->setOpacity(0.0f, false);
57
+ myIconNext = new StGLIcon(this, -getRoot()->scale(48), 0, StGLCorner(ST_VCORNER_CENTER, ST_HCORNER_RIGHT), 1);
58
+ myIconNext->setOpacity(0.0f, false);
59
+
60
params.DisplayMode = new StEnumParam(MODE_STEREO, stCString("viewStereoMode"), stCString("Stereo Output"));
61
params.DisplayMode->defineOption(MODE_STEREO, stCString("Stereo"));
62
params.DisplayMode->defineOption(MODE_ONLY_LEFT, stCString("Left View"));
63
64
65
params.ToHealAnamorphicRatio = new StBoolParamNamed(false, stCString("toHealAnamorphic"), stCString("Heal Anamorphic Ratio"));
66
params.TextureFilter = new StEnumParam(StGLImageProgram::FILTER_LINEAR, stCString("viewTexFilter"), stCString("Texture Filter"));
67
- params.TextureFilter->defineOption(StGLImageProgram::FILTER_NEAREST, stCString("Nearest"));
68
- params.TextureFilter->defineOption(StGLImageProgram::FILTER_LINEAR, stCString("Linear"));
69
- params.TextureFilter->defineOption(StGLImageProgram::FILTER_BLEND, stCString("Blend"));
70
+ params.TextureFilter->defineOption(StGLImageProgram::FILTER_NEAREST, stCString("Nearest"));
71
+ params.TextureFilter->defineOption(StGLImageProgram::FILTER_LINEAR, stCString("Linear"));
72
+ params.TextureFilter->defineOption(StGLImageProgram::FILTER_TRILINEAR, stCString("Trilinear"));
73
+ params.TextureFilter->defineOption(StGLImageProgram::FILTER_BLEND, stCString("Blend"));
74
75
params.Gamma = myProgram.params.gamma;
76
params.Brightness = myProgram.params.brightness;
77
78
StGLContext& aCtx = getContext();
79
myTextureQueue->getQTexture().release(aCtx);
80
myQuad.release(aCtx);
81
+ myCube.release(aCtx);
82
myUVSphere.release(aCtx);
83
+ myHemisphere.release(aCtx);
84
+ myCylinder.release(aCtx);
85
+ myTheater.release(aCtx);
86
myProgram.release(aCtx);
87
88
// simplify debugging - nullify pointer to this widget
89
90
StHandle<StStereoParams> aFileParams = myTextureQueue->getQTexture().getFront(StGLQuadTexture::LEFT_TEXTURE).getSource();
91
if(params.stereoFile != aFileParams) {
92
params.stereoFile = aFileParams;
93
+ myFadeTimer.stop();
94
onParamsChanged();
95
+ } else if(!myHasVideoStream) {
96
+ myFadeTimer.stop();
97
}
98
}
99
}
100
101
aCtx.pushError(StString("Fail to init StGLQuad"));
102
ST_ERROR_LOG("Fail to init StGLQuad");
103
return false;
104
- } else if(!myUVSphere.initVBOs(aCtx)) {
105
+ }/* else if(!myUVSphere.initVBOs(aCtx)) {
106
ST_ERROR_LOG("Fail to init StGLUVSphere");
107
+ }*/
108
+
109
+ // a unit cube for cubemap rendering
110
+ if(!stglInitCube()) {
111
+ return false;
112
}
113
114
// setup texture filter
115
- myTextureQueue->getQTexture().setMinMagFilter(aCtx, params.TextureFilter->getValue() == StGLImageProgram::FILTER_NEAREST ? GL_NEAREST : GL_LINEAR);
116
+ myTextureQueue->getQTexture().setMinMagFilter(aCtx,
117
+ params.TextureFilter->getValue() == StGLImageProgram::FILTER_NEAREST
118
+ ? GL_NEAREST : GL_LINEAR);
119
120
myIsInitialized = true;
121
return myIsInitialized && isInit;
122
}
123
124
+/**
125
+ * Cubemap sides.
126
+ */
127
+enum StCubeSide {
128
+ StCubeSide_PX = 0,
129
+ StCubeSide_NX,
130
+ StCubeSide_PY,
131
+ StCubeSide_NY,
132
+ StCubeSide_PZ,
133
+ StCubeSide_NZ,
134
+};
135
+typedef StVec4<int> StIVec4;
136
+
137
+bool StGLImageRegion::stglInitCube(const StGLVec4& theClamp,
138
+ const StPanorama thePano) {
139
+ myCubeClamp = theClamp;
140
+ myCubePano = thePano;
141
+
142
+ // a unit cube for cubemap rendering
143
+ const StGLVec3 THE_VERTS[8] = {
144
+ StGLVec3(-1.0f,-1.0f, 1.0f),
145
+ StGLVec3( 1.0f,-1.0f, 1.0f),
146
+ StGLVec3(-1.0f, 1.0f, 1.0f),
147
+ StGLVec3( 1.0f, 1.0f, 1.0f),
148
+ StGLVec3(-1.0f,-1.0f,-1.0f),
149
+ StGLVec3( 1.0f,-1.0f,-1.0f),
150
+ StGLVec3(-1.0f, 1.0f,-1.0f),
151
+ StGLVec3( 1.0f, 1.0f,-1.0f)
152
+ };
153
+
154
+ const StIVec4 THE_SIDES[6] = {
155
+ StIVec4(3, 7, 5, 1), // px
156
+ StIVec4(6, 2, 0, 4), // nx
157
+ StIVec4(2, 3, 7, 6), // py
158
+ StIVec4(0, 1, 5, 4), // ny
159
+ StIVec4(0, 1, 3, 2), // pz
160
+ StIVec4(5, 4, 6, 7), // nz
161
+ };
162
+
163
+ StArrayList<StGLVec3>& aVertArr = myCube.changeVertices();
164
+ StArrayList<StGLVec3>& aCoordArr = myCube.changeNormals();
165
+ StArrayList<StGLVec4>& aClampArr = myCube.changeColors();
166
+ aVertArr.initArray(6 * 6);
167
+ aCoordArr.initArray(aVertArr.size());
168
+ aClampArr.initArray(aVertArr.size());
169
+ int aVert = 0;
170
+ for(int aSideIter = 0; aSideIter < 6; ++aSideIter, aVert += 6) {
171
+ StIVec4 aSide = THE_SIDES[aSideIter];
172
+ aVertArr[aVert + 0] = THE_VERTS[aSide[0]];
173
+ aVertArr[aVert + 1] = THE_VERTS[aSide[1]];
174
+ aVertArr[aVert + 2] = THE_VERTS[aSide[2]];
175
+
176
+ aVertArr[aVert + 3] = THE_VERTS[aSide[0]];
177
+ aVertArr[aVert + 4] = THE_VERTS[aSide[2]];
178
+ aVertArr[aVert + 5] = THE_VERTS[aSide[3]];
179
+
180
+ // rotate EAC cube sides
181
+ if(thePano == StPanorama_Cubemap3_2ytb) {
182
+ if(aSideIter == StCubeSide_NY) {
183
+ const StIVec4 aCopy = aSide;
184
+ for(int aSubIter = 0; aSubIter < 4; ++aSubIter) {
185
+ aSide[aSubIter] = aCopy[aSubIter > 0 ? aSubIter - 1 : 3];
186
+ }
187
+ }
188
+ if(aSideIter == StCubeSide_NZ || aSideIter == StCubeSide_PY) {
189
+ const StIVec4 aCopy = aSide;
190
+ for(int aSubIter = 0; aSubIter < 4; ++aSubIter) {
191
+ aSide[aSubIter] = aCopy[aSubIter < 3 ? aSubIter + 1 : 0];
192
+ }
193
+ }
194
+ } else if(thePano == StPanorama_Cubemap2_3ytb) {
195
+ if(aSideIter == StCubeSide_PX
196
+ || aSideIter == StCubeSide_NX) {
197
+ const StIVec4 aCopy = aSide;
198
+ for(int aSubIter = 0; aSubIter < 4; ++aSubIter) {
199
+ aSide[aSubIter] = aCopy[aSubIter < 3 ? aSubIter + 1 : 0];
200
+ }
201
+ }
202
+ if(aSideIter == StCubeSide_PZ) {
203
+ const StIVec4 aCopy = aSide;
204
+ for(int aSubIter = 0; aSubIter < 4; ++aSubIter) {
205
+ aSide[aSubIter] = aCopy[aSubIter > 0 ? aSubIter - 1 : 3];
206
+ }
207
+ }
208
+ }
209
+
210
+ aCoordArr[aVert + 0] = THE_VERTS[aSide[0]];
211
+ aCoordArr[aVert + 1] = THE_VERTS[aSide[1]];
212
+ aCoordArr[aVert + 2] = THE_VERTS[aSide[2]];
213
+
214
+ aCoordArr[aVert + 3] = THE_VERTS[aSide[0]];
215
+ aCoordArr[aVert + 4] = THE_VERTS[aSide[2]];
216
+ aCoordArr[aVert + 5] = THE_VERTS[aSide[3]];
217
+ for(int aSubIter = 0; aSubIter < 6; ++aSubIter) {
218
+ StGLVec4& aClamp = aClampArr[aVert + aSubIter];
219
+ aClamp = StGLVec4(0.0f, 0.0f, 0.0f, theClamp.x());
220
+ switch(aSideIter) {
221
+ case StCubeSide_PX: {
222
+ aClamp.x() = 1.0f;
223
+ aClamp.y() = -theClamp.w();
224
+ aClamp.z() = -theClamp.z();
225
+ break;
226
+ }
227
+ case StCubeSide_NX: {
228
+ aClamp.x() = -1.0f;
229
+ aClamp.y() = -theClamp.w();
230
+ aClamp.z() = theClamp.z();
231
+ break;
232
+ }
233
+ case StCubeSide_PZ: {
234
+ aClamp.x() = -theClamp.z();
235
+ aClamp.y() = -theClamp.w();
236
+ aClamp.z() = 1.0f;
237
+ break;
238
+ }
239
+ case StCubeSide_NZ: {
240
+ aClamp.x() = theClamp.z();
241
+ aClamp.y() = -theClamp.w();
242
+ aClamp.z() = -1.0f;
243
+ break;
244
+ }
245
+ case StCubeSide_PY: {
246
+ aClamp.x() = theClamp.z();
247
+ aClamp.y() = 1.0f;
248
+ aClamp.z() = theClamp.w();
249
+ break;
250
+ }
251
+ case StCubeSide_NY: {
252
+ aClamp.x() = theClamp.z();
253
+ aClamp.y() = -1.0f;
254
+ aClamp.z() = -theClamp.w();
255
+ break;
256
+ }
257
+ }
258
+ }
259
+ }
260
+
261
+ // triangle strip initialization
262
+ /*aCubeVerts.initArray(8);
263
+ for(int aVertIter = 0; aVertIter < 8; ++aVertIter) {
264
+ aCubeVerts[aVertIter] = THE_VERTS[aVertIter];
265
+ }
266
+ const GLuint THE_BOX_TRISTRIP[14] = { 0, 1, 2, 3, 7, 1, 5, 4, 7, 6, 2, 4, 0, 1 };
267
+ StArrayList<GLuint>& aCubeInd = myCube.changeIndices();
268
+ aCubeInd.initArray(14);
269
+ for(unsigned int aVertIter = 0; aVertIter < 14; ++aVertIter) {
270
+ aCubeInd[aVertIter] = THE_BOX_TRISTRIP[aVertIter];
271
+ }*/
272
+
273
+ StGLContext& aCtx = getContext();
274
+ if(!myCube.initVBOs(aCtx)) {
275
+ aCtx.pushError(StString("Fail to init Cube Mesh"));
276
+ ST_ERROR_LOG("Fail to init Cube Mesh");
277
+ return false;
278
+ }
279
+ return true;
280
+}
281
+
282
StGLVec2 StGLImageRegion::getMouseMoveFlat(const StPointD_t& theCursorZoFrom,
283
const StPointD_t& theCursorZoTo) const {
284
// apply scale factor in case of working area margins
285
286
float aYaw = -stToRadians(aParams->getPanYaw() + aMouseMove.x()) + aYawShift;
287
float aPitch = stToRadians(StStereoParams::clipPitch(aParams->getPanPitch() + aMouseMove.y()));
288
float aRoll = stToRadians(aParams->getZRotate());
289
+ if(myProjCam.isCustomProjection()) {
290
+ aPitch = 0.0f; // ignore pitch for HMD
291
+ }
292
293
// apply separation
294
const float aSepDeltaX = GLfloat(aParams->getSeparationDx()) * 0.05f;
295
296
}
297
298
void StGLImageRegion::stglDraw(unsigned int theView) {
299
+ myIconPrev->setOpacity(0.0f, false);
300
+ myIconNext->setOpacity(0.0f, false);
301
StHandle<StStereoParams> aParams = getSource();
302
if(!myIsInitialized || !isVisible() || aParams.isNull()
303
|| !myTextureQueue->getQTexture().getFront(StGLQuadTexture::LEFT_TEXTURE).isValid()
304
305
void StGLImageRegion::stglDrawView(unsigned int theView) {
306
StGLQuadTexture::LeftOrRight aLeftOrRight = StGLQuadTexture::LEFT_TEXTURE;
307
StHandle<StStereoParams> aParams = getSource();
308
+ mySampleRatio = 1.0f;
309
+ myFrameSize = StVec2<int>(0, 0);
310
if(!myIsInitialized || aParams.isNull()) {
311
return;
312
}
313
314
}
315
}
316
317
- // setup scissor box
318
- StGLBoxPx aScissorBox;
319
- const StRectI_t aFrameRectAbs = getAbsolute(aFrameRectPx);
320
- getRoot()->stglScissorRect(aFrameRectAbs, aScissorBox);
321
- aCtx.stglSetScissorRect(aScissorBox, true);
322
- aCtx.stglResizeViewport(aScissorBox);
323
+ // set 85 degrees FOV as 1.0x zoom for panorama rendering
324
+ myProjCam = *getCamera();
325
myProjCam.resize(aCameraAspect);
326
+ myProjCam.setFOVy(85.0f);
327
328
aCtx.core20fwd->glDisable(GL_BLEND);
329
330
StGLFrameTextures& aTextures = myTextureQueue->getQTexture().getFront(aLeftOrRight);
331
- aTextures.bind(aCtx);
332
333
StGLVec2 aTextureSize (GLfloat(aTextures.getPlane(0).getSizeX()),
334
GLfloat(aTextures.getPlane(0).getSizeY()));
335
StGLVec2 aTextureUVSize(GLfloat(aTextures.getPlane(1).getSizeX()),
336
GLfloat(aTextures.getPlane(1).getSizeY()));
337
+ StGLVec2 aTextureASize (GLfloat(aTextures.getPlane(3).getSizeX()),
338
+ GLfloat(aTextures.getPlane(3).getSizeY()));
339
StGLMatrix aModelMat;
340
// data rectangle in the texture
341
- StGLVec4 aClampVec, aClampUV;
342
+ StGLVec4 aClampVec(0.0f, 0.0f, 1.0f, 1.0f), aClampUV(0.0f, 0.0f, 1.0f, 1.0f), aClampA(0.0f, 0.0f, 1.0f, 1.0f);
343
if(params.TextureFilter->getValue() == StGLImageProgram::FILTER_NEAREST) {
344
myTextureQueue->getQTexture().setMinMagFilter(aCtx, GL_NEAREST);
345
//
346
347
aClampUV.y() = 0.0f;
348
aClampUV.z() = aTextures.getPlane(1).getDataSize().x();
349
aClampUV.w() = aTextures.getPlane(1).getDataSize().y();
350
+ // Alpha
351
+ aClampA.x() = 0.0f;
352
+ aClampA.y() = 0.0f;
353
+ aClampA.z() = aTextures.getPlane(3).getDataSize().x();
354
+ aClampA.w() = aTextures.getPlane(3).getDataSize().y();
355
} else {
356
- myTextureQueue->getQTexture().setMinMagFilter(aCtx, GL_LINEAR);
357
- //
358
- aClampVec.x() = 0.5f / aTextureSize.x();
359
- aClampVec.y() = 0.5f / aTextureSize.y();
360
- aClampVec.z() = aTextures.getPlane(0).getDataSize().x() - 2.0f * aClampVec.x();
361
- aClampVec.w() = aTextures.getPlane(0).getDataSize().y() - 2.0f * aClampVec.y();
362
+ if(params.TextureFilter->getValue() == StGLImageProgram::FILTER_TRILINEAR) {
363
+ myTextureQueue->getQTexture().setMinMagFilter(aCtx, GL_LINEAR_MIPMAP_LINEAR, GL_LINEAR);
364
+ } else {
365
+ myTextureQueue->getQTexture().setMinMagFilter(aCtx, GL_LINEAR);
366
+ }
367
+
368
+ // clamping is undesired for full-range cubemap to allow smooth seamless cube boundaries,
369
+ // but EAC video normally defines non-square cube sides requiring clamping
370
+ const bool isCubemapFull = aTextures.getPlane().getTarget() == GL_TEXTURE_CUBE_MAP
371
+ && aTextures.getPlane().getPackedPanorama() != StPanorama_Cubemap3_2ytb
372
+ && aTextures.getPlane().getPackedPanorama() != StPanorama_Cubemap2_3ytb;
373
+ if(!isCubemapFull
374
+ || aTextures.getPlane(0).getDataSize().x() != aTextures.getPlane(0).getDataSize().y()
375
+ || aTextures.getPlane(0).getDataSize().x() != 1.0f) {
376
+ aClampVec.x() = 0.5f / aTextureSize.x();
377
+ aClampVec.y() = 0.5f / aTextureSize.y();
378
+ aClampVec.z() = aTextures.getPlane(0).getDataSize().x() - 2.0f * aClampVec.x();
379
+ aClampVec.w() = aTextures.getPlane(0).getDataSize().y() - 2.0f * aClampVec.y();
380
+ }
381
// UV
382
if(aTextureUVSize.x() > 0.0f
383
&& aTextureUVSize.y() > 0.0f) {
384
- aClampUV.x() = 0.5f / aTextureUVSize.x();
385
- aClampUV.y() = 0.5f / aTextureUVSize.y(),
386
- aClampUV.z() = aTextures.getPlane(1).getDataSize().x() - 2.0f * aClampUV.x();
387
- aClampUV.w() = aTextures.getPlane(1).getDataSize().y() - 2.0f * aClampUV.y();
388
+ if(!isCubemapFull
389
+ || aTextures.getPlane(1).getDataSize().x() != aTextures.getPlane(1).getDataSize().y()
390
+ || aTextures.getPlane(1).getDataSize().x() != 1.0f) {
391
+ aClampUV.x() = 0.5f / aTextureUVSize.x();
392
+ aClampUV.y() = 0.5f / aTextureUVSize.y(),
393
+ aClampUV.z() = aTextures.getPlane(1).getDataSize().x() - 2.0f * aClampUV.x();
394
+ aClampUV.w() = aTextures.getPlane(1).getDataSize().y() - 2.0f * aClampUV.y();
395
+ }
396
+ }
397
+ // Alpha
398
+ if(aTextureASize.x() > 0.0f
399
+ && aTextureASize.y() > 0.0f) {
400
+ if(!isCubemapFull
401
+ || aTextures.getPlane(3).getDataSize().x() != aTextures.getPlane(3).getDataSize().y()
402
+ || aTextures.getPlane(3).getDataSize().x() != 1.0f) {
403
+ aClampA.x() = 0.5f / aTextureASize.x();
404
+ aClampA.y() = 0.5f / aTextureASize.y(),
405
+ aClampA.z() = aTextures.getPlane(3).getDataSize().x() - 2.0f * aClampA.x();
406
+ aClampA.w() = aTextures.getPlane(3).getDataSize().y() - 2.0f * aClampA.y();
407
+ }
408
}
409
}
410
+ aTextures.bind(aCtx);
411
412
// select (de)anaglyph color filter
413
StGLVec3 aColorScale(1.0f, 1.0f, 1.0f);
414
415
const GLfloat aScaleBack = aParams->ScaleFactor;
416
const StGLVec2 aPanBack = aParams->PanCenter;
417
418
- const float aVrScale = float(myRoot->getVrZoomOut());
419
-
420
StViewSurface aViewMode = aParams->ViewingMode;
421
if(aTextures.getPlane(0).getTarget() == GL_TEXTURE_CUBE_MAP) {
422
- aViewMode = StViewSurface_Cubemap;
423
- } else if(aViewMode == StViewSurface_Cubemap) {
424
+ if(aViewMode != StViewSurface_Cubemap && aViewMode != StViewSurface_CubemapEAC) {
425
+ aViewMode = aTextures.getPlane().getPackedPanorama() == StPanorama_Cubemap3_2ytb
426
+ || aTextures.getPlane().getPackedPanorama() == StPanorama_Cubemap2_3ytb
427
+ ? StViewSurface_CubemapEAC
428
+ : StViewSurface_Cubemap;
429
+ }
430
+ } else if(aViewMode == StViewSurface_Cubemap || aViewMode == StViewSurface_CubemapEAC) {
431
aViewMode = StViewSurface_Plain;
432
}
433
434
+ // setup scissor box
435
+ StGLBoxPx aScissorBox;
436
+ const StRectI_t aFrameRectAbs = getAbsolute(aFrameRectPx);
437
+ if(aViewMode == StViewSurface_Plain) {
438
+ getRoot()->stglScissorRect2d(aFrameRectAbs, aScissorBox);
439
+ } else {
440
+ getRoot()->stglScissorRect3d(aFrameRectAbs, aScissorBox);
441
+ }
442
+ aCtx.stglSetScissorRect(aScissorBox, true);
443
+ aCtx.stglResizeViewport(aScissorBox);
444
+
445
+ myFrameSize.x() = int(double(aTextures.getPlane().getDataSize().x()) * double(aTextures.getPlane().getSizeX()));
446
+ myFrameSize.y() = int(double(aTextures.getPlane().getDataSize().y()) * double(aTextures.getPlane().getSizeY()));
447
+ mySampleRatio = aTextures.getPlane().getPixelRatio();
448
+
449
myProgram.setColorScale(aColorScale); // apply de-anaglyph color filter
450
StGLImageProgram::FragGetColor aColorGetter = params.TextureFilter->getValue() == StGLImageProgram::FILTER_BLEND
451
? StGLImageProgram::FragGetColor_Blend
452
: StGLImageProgram::FragGetColor_Normal;
453
+ const bool toDragImageInSwipe = getRectPx().ratio() < 0.75; // drag image only in portrait mode while swiping
454
switch(aViewMode) {
455
case StViewSurface_Plain: {
456
- if(!myProgram.init(aCtx, aTextures.getColorModel(), aTextures.getColorScale(), aColorGetter)) {
457
- break;
458
- }
459
-
460
- myProgram.getActiveProgram()->use(aCtx);
461
-
462
- // setup data rectangle in the texture
463
- myProgram.setTextureSizePx (aCtx, aTextureSize);
464
- myProgram.setTextureMainDataSize(aCtx, aClampVec);
465
- myProgram.setTextureUVDataSize (aCtx, aClampUV);
466
-
467
- // handle dragging timer
468
- if( isClicked(ST_MOUSE_LEFT)
469
- && !myIsClickAborted
470
- && myClickTimer.isOn()) {
471
- if(myClickTimer.getElapsedTimeInMilliSec() < myDragDelayMs) {
472
- const StPointD_t aCurr = getRoot()->getCursorZo();
473
- const int aDx = int((aCurr.x() - myClickPntZo.x()) * double(getRectPx().width()));
474
- const int aDy = int((aCurr.y() - myClickPntZo.y()) * double(getRectPx().height()));
475
- if(std::abs(aDx) > myRoot->getClickThreshold()
476
- || std::abs(aDy) > myRoot->getClickThreshold()) {
477
- myIsClickAborted = true;
478
+ const float aBrightnessBack = params.Brightness->getValue();
479
+ const double aDragDelayMs = myDragDelayMs > 0.0 ? myDragDelayMs : myDragDelayTmpMs;
480
+ if(isClicked(ST_MOUSE_LEFT)) {
481
+ // handle dragging timer
482
+ if(!myIsClickAborted
483
+ && myClickTimer.isOn()) {
484
+ if(myClickTimer.getElapsedTimeInMilliSec() < aDragDelayMs) {
485
+ const StPointD_t aCurr = getRoot()->getCursorZo();
486
+ const int aDx = int((aCurr.x() - myClickPntZo.x()) * double(getRectPx().width()));
487
+ const int aDy = int((aCurr.y() - myClickPntZo.y()) * double(getRectPx().height()));
488
+ if(std::abs(aDx) > myRoot->getClickThreshold()
489
+ || std::abs(aDy) > myRoot->getClickThreshold()) {
490
+ myIsClickAborted = true;
491
+ myClickTimer.stop();
492
+ }
493
+ } else {
494
myClickTimer.stop();
495
}
496
- } else {
497
- myClickTimer.stop();
498
}
499
- }
500
501
- // handle dragging
502
- if( isClicked(ST_MOUSE_LEFT)
503
- && !myIsClickAborted
504
- && !myClickTimer.isOn()) {
505
- const GLfloat aRectRatio = GLfloat(getRectPx().ratio());
506
- aParams->moveFlat(getMouseMoveFlat(myClickPntZo, getRoot()->getCursorZo()), aRectRatio);
507
- if(myDragDelayMs > 1.0) {
508
- const GLfloat aScaleSteps = 0.1f;
509
- const StPointD_t aCenterCursor(0.5, 0.5);
510
- const StGLVec2 aVec = getMouseMoveFlat(aCenterCursor, getRoot()->getCursorZo()) * (-aScaleSteps);
511
- aParams->scaleIn(aScaleSteps);
512
- aParams->moveFlat(aVec, aRectRatio);
513
+ // handle dragging
514
+ if(!myIsClickAborted
515
+ && !myClickTimer.isOn()) {
516
+ // panning
517
+ const GLfloat aRectRatio = GLfloat(getRectPx().ratio());
518
+ aParams->moveFlat(getMouseMoveFlat(myClickPntZo, getRoot()->getCursorZo()), aRectRatio);
519
+ if(aDragDelayMs > 1.0) {
520
+ const GLfloat aScaleSteps = 0.1f;
521
+ const StPointD_t aCenterCursor(0.5, 0.5);
522
+ const StGLVec2 aVec = getMouseMoveFlat(aCenterCursor, getRoot()->getCursorZo()) * (-aScaleSteps);
523
+ aParams->scaleIn(aScaleSteps);
524
+ aParams->moveFlat(aVec, aRectRatio);
525
+ }
526
+ } else if(!myList.isNull()) {
527
+ // previous / next swipe gesture
528
+ const double anIntensMult = toDragImageInSwipe ? 1.0 : 3.0;
529
+ const StPlayList::CurrentPosition aPos = myList->getCurrentPosition();
530
+ const double aMouseDX = myClickPntZo.x() - getRoot()->getCursorZo().x();
531
+ const float aScaleSteps = (float )stMin(std::abs(aMouseDX) * anIntensMult, 1.0);
532
+ if(aMouseDX < 0.0) {
533
+ // previous
534
+ if(aPos == StPlayList::CurrentPosition_Middle
535
+ || aPos == StPlayList::CurrentPosition_Last) {
536
+ //params.Brightness->setValue(aBrightnessBack - aScaleSteps);
537
+ //aParams->scaleIn(-aScaleSteps);
538
+ if(toDragImageInSwipe) {
539
+ StGLVec2 aVec = getMouseMoveFlat(myClickPntZo, getRoot()->getCursorZo());
540
+ aVec.y() = 0.0;
541
+ aParams->moveFlat(aVec, float(getRectPx().ratio()));
542
+ }
543
+ myIconPrev->setOpacity(aScaleSteps, false);
544
+ }
545
+ } else {
546
+ // next
547
+ if(aPos == StPlayList::CurrentPosition_Middle
548
+ || aPos == StPlayList::CurrentPosition_First) {
549
+ if(toDragImageInSwipe) {
550
+ StGLVec2 aVec = getMouseMoveFlat(myClickPntZo, getRoot()->getCursorZo());
551
+ aVec.y() = 0.0;
552
+ aParams->moveFlat(aVec, float(getRectPx().ratio()));
553
+ }
554
+ myIconNext->setOpacity(aScaleSteps, false);
555
+ }
556
+ }
557
+ }
558
+ } else if(myFadeTimer.isOn()) {
559
+ static const double THE_FADE_ANIM_MS = 1000.0;
560
+ const double aProgress = myFadeTimer.getElapsedTimeInMilliSec() / THE_FADE_ANIM_MS;
561
+ const double aFadeClamp = stMin(1.0, aProgress);
562
+ const bool isNext = myFadeFrom.x() < myClickPntZo.x();
563
+ if(toDragImageInSwipe) {
564
+ StPointD_t aFadeTo = myFadeFrom;
565
+ aFadeTo.x() += isNext ? -aFadeClamp : aFadeClamp;
566
+
567
+ StGLVec2 aVec = getMouseMoveFlat(myClickPntZo, aFadeTo);
568
+ aVec.y() = 0.0;
569
+ aParams->moveFlat(aVec, float(getRectPx().ratio()));
570
}
571
+ params.Brightness->setValue(aBrightnessBack - (float )aFadeClamp * 3.0f);
572
+
573
+ // animate icon opacity in loop
574
+ const double anIntensMult = toDragImageInSwipe ? 1.0 : 3.0;
575
+ const double anOpacityFrom = stMin(std::abs(myClickPntZo.x() - myFadeFrom.x()) * anIntensMult, 1.0);
576
+ double anIconProgress = anOpacityFrom + aProgress;
577
+ const bool isEven = (int(anIconProgress) % 2) == 0;
578
+ anIconProgress -= int(anIconProgress);
579
+ if(!isEven) { anIconProgress = 1.0 - anIconProgress; }
580
+ StGLIcon* anIcon = isNext ? myIconNext : myIconPrev;
581
+ anIcon->setOpacity((float )anIconProgress, false);
582
}
583
584
GLfloat anXRotate = aParams->getXRotate();
585
586
}
587
588
// apply scale
589
+ const float aVrScale = float(myRoot->getVrZoomOut());
590
aModelMat.scale(aParams->ScaleFactor * aVrScale, aParams->ScaleFactor * aVrScale, 1.0f);
591
592
// apply position
593
594
case StFormat_SideBySide_RL: {
595
if(aDispRatio >= 0.85 && aDispRatio <= 1.18) {
596
aDispRatio *= 2.0;
597
+ mySampleRatio *= 2.0f;
598
}
599
break;
600
}
601
602
case StFormat_TopBottom_RL: {
603
if(aDispRatio >= 3.5 && aDispRatio <= 4.8) {
604
aDispRatio *= 0.5;
605
+ mySampleRatio *= 0.5f;
606
}
607
break;
608
}
609
610
aModelMat.translate(StGLVec3( aSepDeltaX * 0.5f, aSepDeltaY * 0.5f, 0.0f));
611
}
612
613
- StGLMatrix anOrthoMat;
614
- anOrthoMat.initOrtho(StGLVolume(-aRectRatio * aFrustrumL, aRectRatio * aFrustrumR,
615
- -1.0f * aFrustrumB, 1.0f * aFrustrumT,
616
- -1.0f, 1.0f));
617
- myProgram.getActiveProgram()->setProjMat (aCtx, anOrthoMat);
618
- myProgram.getActiveProgram()->setModelMat(aCtx, aModelMat);
619
+ if(myProgram.init(aCtx, aTextures.getColorModel(), aTextures.getColorScale(), aColorGetter)) {
620
+ myProgram.getActiveProgram()->use(aCtx);
621
622
- myQuad.draw(aCtx, *myProgram.getActiveProgram());
623
+ // setup data rectangle in the texture
624
+ myProgram.setTextureSizePx (aCtx, aTextureSize);
625
+ myProgram.setTextureMainDataSize(aCtx, aClampVec);
626
+ myProgram.setTextureUVDataSize (aCtx, aClampUV);
627
+ myProgram.setTextureADataSize (aCtx, aClampA);
628
629
- myProgram.getActiveProgram()->unuse(aCtx);
630
+ StGLMatrix anOrthoMat;
631
+ anOrthoMat.initOrtho(StGLVolume(-aRectRatio * aFrustrumL, aRectRatio * aFrustrumR,
632
+ -1.0f * aFrustrumB, 1.0f * aFrustrumT,
633
+ -1.0f, 1.0f));
634
+ myProgram.getActiveProgram()->setProjMat (aCtx, anOrthoMat);
635
+ myProgram.getActiveProgram()->setModelMat(aCtx, aModelMat);
636
+
637
+ myQuad.draw(aCtx, *myProgram.getActiveProgram());
638
+
639
+ myProgram.getActiveProgram()->unuse(aCtx);
640
+ }
641
642
// restore changed parameters
643
aParams->ScaleFactor = aScaleBack;
644
aParams->PanCenter = aPanBack;
645
+ params.Brightness->setValue(aBrightnessBack);
646
break;
647
}
648
- case StViewSurface_Cubemap: {
649
- if(!myProgram.init(aCtx, aTextures.getColorModel(), aTextures.getColorScale(), StGLImageProgram::FragGetColor_Cubemap)) {
650
+ case StViewSurface_Cubemap:
651
+ case StViewSurface_CubemapEAC: {
652
+ // Clamping range is passed through vertex attributes.
653
+ // To avoid extra vertex attributes, the smallest clamping range is used across planes.
654
+ // This trick is possible, because cubemap texture lazy resizing is not used,
655
+ // hence all planes should have same proportions.
656
+ // The result will be broken for rare formats like YUV422P/YUV411P/YUV440P.
657
+ StGLVec4 aClamVecMin = aClampVec;
658
+ if(aTextureUVSize.x() > 0.0f
659
+ && aTextureUVSize.y() > 0.0f) {
660
+ aClamVecMin.x() = stMax(aClamVecMin.x(), aClampUV.x());
661
+ aClamVecMin.y() = stMax(aClamVecMin.y(), aClampUV.y());
662
+ aClamVecMin.z() = stMin(aClamVecMin.z(), aClampUV.z());
663
+ aClamVecMin.w() = stMin(aClamVecMin.w(), aClampUV.w());
664
+ }
665
+ if(aTextureASize.x() > 0.0f
666
+ && aTextureASize.y() > 0.0f) {
667
+ aClamVecMin.x() = stMax(aClamVecMin.x(), aClampA.x());
668
+ aClamVecMin.y() = stMax(aClamVecMin.y(), aClampA.y());
669
+ aClamVecMin.z() = stMin(aClamVecMin.z(), aClampA.z());
670
+ aClamVecMin.w() = stMin(aClamVecMin.w(), aClampA.w());
671
+ }
672
+
673
+ if(myCubeClamp != aClamVecMin
674
+ || myCubePano != aTextures.getPlane().getPackedPanorama()) {
675
+ stglInitCube(aClamVecMin, aTextures.getPlane().getPackedPanorama());
676
+ }
677
+
678
+ if(!myProgram.init(aCtx, aTextures.getColorModel(), aTextures.getColorScale(),
679
+ StGLImageProgram::FragGetColor_Cubemap,
680
+ aViewMode == StViewSurface_CubemapEAC ? StGLImageProgram::FragTexEAC_On : StGLImageProgram::FragTexEAC_Off)) {
681
break;
682
}
683
684
685
myProgram.setTextureSizePx (aCtx, aTextureSize);
686
myProgram.setTextureMainDataSize(aCtx, aClampVec);
687
myProgram.setTextureUVDataSize (aCtx, aClampUV);
688
+ myProgram.setTextureADataSize (aCtx, aClampA);
689
myProgram.setCubeTextureFlipZ (aCtx, aParams->ToFlipCubeZ);
690
691
- const float aScale = THE_PANORAMA_DEF_ZOOM * aParams->ScaleFactor * aVrScale;
692
+ const float aScale = aParams->ScaleFactor;
693
aModelMat.scale(aScale, aScale, 1.0f);
694
695
// compute orientation
696
const StGLQuaternion anOri = getHeadOrientation(theView, true);
697
aModelMat = StGLMatrix::multiply(aModelMat, StGLMatrix(anOri));
698
-
699
- StGLMatrix aMatModelInv, aMatProjInv;
700
- aModelMat.inverted(aMatModelInv);
701
- myProjCam.getProjMatrixMono().inverted(aMatProjInv);
702
- myProgram.getActiveProgram()->setProjMat (aCtx, StGLMatrix::multiply(aMatModelInv, aMatProjInv));
703
myProgram.getActiveProgram()->setModelMat(aCtx, aModelMat);
704
705
- ///glEnable(GL_TEXTURE_CUBE_MAP_SEAMLESS);
706
+ if(myProjCam.isCustomProjection()) {
707
+ myProgram.getActiveProgram()->setProjMat (aCtx, myProjCam.getProjMatrix());
708
+ } else {
709
+ myProgram.getActiveProgram()->setProjMat (aCtx, myProjCam.getProjMatrixMono());
710
+ }
711
712
- myQuad.draw(aCtx, *myProgram.getActiveProgram());
713
+ #if !defined(GL_ES_VERSION_2_0)
714
+ // Issues with seamless cubemap filtering:
715
+ // - Desktop, available since OpenGL 3.2+ (or ARB_seamless_cube_map) and DISABLED by default;
716
+ // some old implementations might be buggy;
717
+ // some very old implementation might even switch to software fallback.
718
+ // - Mobile, OpenGL ES 3.0 requires cubemap filtering to be always ENABLED - no API for disabling;
719
+ // OpenGL ES 3.0 implementations might not support seamless filtering without a way to detect it.
720
+ // - Seamless filtering works is desired for a proper cubemap definition,
721
+ // but undesired for EAC video frames with non-square cube sides and has rotated sides.
722
+ if(aCtx.isGlGreaterEqual(3, 2)) {
723
+ ///glEnable(GL_TEXTURE_CUBE_MAP_SEAMLESS);
724
+ }
725
+ #endif
726
+ myCube.draw(aCtx, *myProgram.getActiveProgram());
727
728
myProgram.getActiveProgram()->unuse(aCtx);
729
730
731
aParams->PanCenter = aPanBack;
732
break;
733
}
734
+ case StViewSurface_Cylinder:
735
+ case StViewSurface_Theater:
736
+ case StViewSurface_Hemisphere:
737
case StViewSurface_Sphere: {
738
if(!myProgram.init(aCtx, aTextures.getColorModel(), aTextures.getColorScale(), aColorGetter)) {
739
break;
740
}
741
742
+ StGLMesh* aMesh = &myUVSphere;
743
+ if(aViewMode == StViewSurface_Hemisphere) {
744
+ aMesh = &myHemisphere;
745
+ } else if(aViewMode == StViewSurface_Cylinder) {
746
+ aMesh = &myCylinder;
747
+ const StGLVec2 aSrcSize (aTextures.getPlane().getDataSize().x() * (float )aTextures.getPlane().getSizeX(),
748
+ aTextures.getPlane().getDataSize().y() * (float )aTextures.getPlane().getSizeY());
749
+ float aCylHeight = float(2.0 * M_PI * aSrcSize.y()) / aSrcSize.x();
750
+ //aVertScale *= aTextures.getPlane().getDisplayRatio();
751
+ if(myCylinder.getHeight() != aCylHeight) {
752
+ myCylinder.setHeight(aCylHeight);
753
+ myCylinder.release(aCtx);
754
+ }
755
+ } else if(aViewMode == StViewSurface_Theater) {
756
+ aMesh = &myTheater;
757
+ const float aCylWidth = float(M_PI * myTheater.getRadius() / myTheater.getAngle());
758
+ const float aCylHeight = (aCylWidth / aTextures.getPlane().getDisplayRatio()) * 0.75f;
759
+ if(myTheater.getHeight() != aCylHeight) {
760
+ myTheater.setHeight(aCylHeight);
761
+ myTheater.release(aCtx);
762
+ }
763
+ }
764
+ if(!aMesh->changeVBO(ST_VBO_VERTEX)->isValid()) {
765
+ if(!aMesh->initVBOs(aCtx)) {
766
+ aCtx.pushError(StString("Fail to init mesh data"));
767
+ ST_ERROR_LOG("Fail to init mesh data");
768
+ break;
769
+ }
770
+ }
771
+
772
// perform scaling
773
- const float aScale = THE_SPHERE_RADIUS * THE_PANORAMA_DEF_ZOOM * aParams->ScaleFactor * aVrScale;
774
+ const float aScale = THE_SPHERE_RADIUS * aParams->ScaleFactor;
775
aModelMat.scale(aScale, aScale, THE_SPHERE_RADIUS);
776
777
// compute orientation
778
779
myProgram.setTextureSizePx (aCtx, aTextureSize);
780
myProgram.setTextureMainDataSize(aCtx, aClampVec);
781
myProgram.setTextureUVDataSize (aCtx, aClampUV);
782
+ myProgram.setTextureADataSize (aCtx, aClampA);
783
784
- myProgram.getActiveProgram()->setProjMat (aCtx, myProjCam.getProjMatrixMono());
785
myProgram.getActiveProgram()->setModelMat(aCtx, aModelMat);
786
+ if(myProjCam.isCustomProjection()) {
787
+ myProgram.getActiveProgram()->setProjMat (aCtx, myProjCam.getProjMatrix());
788
+ } else {
789
+ myProgram.getActiveProgram()->setProjMat (aCtx, myProjCam.getProjMatrixMono());
790
+ }
791
792
- myUVSphere.draw(aCtx, *myProgram.getActiveProgram());
793
+ aMesh->draw(aCtx, *myProgram.getActiveProgram());
794
795
myProgram.getActiveProgram()->unuse(aCtx);
796
break;
797
798
bool StGLImageRegion::tryClick(const StClickEvent& theEvent,
799
bool& theIsItemClicked) {
800
StHandle<StStereoParams> aParams = getSource();
801
- if(!myIsInitialized || aParams.isNull()) {
802
+ const bool hasImage = !aParams.isNull()
803
+ && myHasVideoStream
804
+ && myTextureQueue->getQTexture().getFront(StGLQuadTexture::LEFT_TEXTURE).isValid();
805
+ if(!myIsInitialized || !hasImage) {
806
return false;
807
}
808
809
810
myClickPntZo = StPointD_t(theEvent.PointX, theEvent.PointY);
811
myClickTimer.restart();
812
myIsClickAborted = false;
813
+
814
+ myDragDelayTmpMs = 0.0f;
815
+ if(aParams->ViewingMode == StViewSurface_Plain
816
+ && fabs(aParams->ScaleFactor - 1.0f) < 0.00001f
817
+ && fabs(aParams->PanCenter.x()) < 0.00001f
818
+ && fabs(aParams->PanCenter.y()) < 0.00001f) {
819
+ myDragDelayTmpMs = 250.0;
820
+ }
821
}
822
theIsItemClicked = true;
823
return true;
824
825
bool StGLImageRegion::tryUnClick(const StClickEvent& theEvent,
826
bool& theIsItemUnclicked) {
827
StHandle<StStereoParams> aParams = getSource();
828
- if(!myIsInitialized || aParams.isNull()) {
829
+ const bool hasImage = !aParams.isNull()
830
+ && myHasVideoStream
831
+ && myTextureQueue->getQTexture().getFront(StGLQuadTexture::LEFT_TEXTURE).isValid();
832
+ if(!myIsInitialized || !hasImage) {
833
if(isClicked(theEvent.Button)) {
834
theIsItemUnclicked = true;
835
setClicked(theEvent.Button, false);
836
837
case StViewSurface_Plain: {
838
if(!myIsClickAborted) {
839
aParams->moveFlat(getMouseMoveFlat(myClickPntZo, aCursor), GLfloat(getRectPx().ratio()));
840
+ } else if(!myList.isNull()) {
841
+ // previous / next swipe gesture
842
+ StPlayList::CurrentPosition aPos = myList->getCurrentPosition();
843
+ const double aMouseDX = myClickPntZo.x() - getRoot()->getCursorZo().x();
844
+ if(std::abs(aMouseDX) >= 0.25) {
845
+ if(aMouseDX < 0.0) {
846
+ if(aPos == StPlayList::CurrentPosition_Middle
847
+ || aPos == StPlayList::CurrentPosition_Last) {
848
+ if(myList->walkToPrev()) {
849
+ signals.onOpenItem();
850
+ myFadeTimer.restart();
851
+ myFadeFrom = getRoot()->getCursorZo();
852
+ }
853
+ }
854
+ } else {
855
+ if(aPos == StPlayList::CurrentPosition_Middle
856
+ || aPos == StPlayList::CurrentPosition_First) {
857
+ if(myList->walkToNext()) {
858
+ signals.onOpenItem();
859
+ myFadeTimer.restart();
860
+ myFadeFrom = getRoot()->getCursorZo();
861
+ }
862
+ }
863
+ }
864
+ }
865
}
866
break;
867
}
868
case StViewSurface_Cubemap:
869
+ case StViewSurface_CubemapEAC:
870
+ case StViewSurface_Cylinder:
871
+ case StViewSurface_Theater:
872
+ case StViewSurface_Hemisphere:
873
case StViewSurface_Sphere: {
874
aParams->moveSphere(getMouseMoveSphere(myClickPntZo, aCursor));
875
break;
876
877
return false;
878
}
879
880
- const GLfloat SCALE_STEPS = fabs(theEvent.DeltaY) * 0.01f;
881
- if(theEvent.DeltaY > 0.001f) {
882
- if((myKeyFlags & ST_VF_CONTROL) == ST_VF_CONTROL) {
883
- if((myKeyFlags & ST_VF_SHIFT) == ST_VF_SHIFT) {
884
+ if((myKeyFlags & ST_VF_CONTROL) == ST_VF_CONTROL) {
885
+ if(theEvent.StepsY == 0) {
886
+ return false;
887
+ }
888
+ if((myKeyFlags & ST_VF_SHIFT) == ST_VF_SHIFT) {
889
+ if(theEvent.StepsY > 0) {
890
doParamsSepZDec(0.01);
891
} else {
892
- doParamsSepX(size_t(-1));
893
- }
894
- return true;
895
- } else if((myKeyFlags & ST_VF_SHIFT) == ST_VF_SHIFT) {
896
- doParamsSepY(size_t(-1));
897
- return true;
898
- }
899
-
900
- scaleAt(aCursor, SCALE_STEPS);
901
- } else if(theEvent.DeltaY < -0.001f) {
902
- if((myKeyFlags & ST_VF_CONTROL) == ST_VF_CONTROL) {
903
- if((myKeyFlags & ST_VF_SHIFT) == ST_VF_SHIFT) {
904
doParamsSepZInc(0.01);
905
- } else {
906
- doParamsSepX(size_t(1));
907
}
908
- return true;
909
- } else if((myKeyFlags & ST_VF_SHIFT) == ST_VF_SHIFT) {
910
- doParamsSepY(size_t(1));
911
- return true;
912
+ } else {
913
+ doParamsSepX(theEvent.StepsY > 0 ? size_t(-1) : size_t(1));
914
+ }
915
+ return true;
916
+ } else if((myKeyFlags & ST_VF_SHIFT) == ST_VF_SHIFT) {
917
+ if(theEvent.StepsY == 0) {
918
+ return false;
919
}
920
+ doParamsSepY(theEvent.StepsY > 0 ? size_t(-1) : size_t(1));
921
+ return true;
922
+ }
923
924
+ const GLfloat SCALE_STEPS = fabs(theEvent.DeltaY) * 0.1f;
925
+ if(theEvent.DeltaY > 0.0001f) {
926
+ scaleAt(aCursor, SCALE_STEPS);
927
+ } else if(theEvent.DeltaY < -0.0001f) {
928
scaleAt(aCursor, -SCALE_STEPS);
929
}
930
return true;
931
932
break;
933
}
934
case StViewSurface_Cubemap:
935
+ case StViewSurface_CubemapEAC:
936
+ case StViewSurface_Cylinder:
937
+ case StViewSurface_Theater:
938
+ case StViewSurface_Hemisphere:
939
case StViewSurface_Sphere: {
940
if(theStep < 0.0f
941
&& aParams->ScaleFactor <= 0.24f) {
942
sview-17_04.tar.gz/StGLWidgets/StGLMessageBox.cpp -> sview-20_08.tar.gz/StGLWidgets/StGLMessageBox.cpp
Changed
68
1
2
3
void StGLMessageBox::create(const StString& theTitle,
4
const StString& theText,
5
- const int theWidth,
6
- const int theHeight) {
7
+ const int theWidth,
8
+ const int theHeight,
9
+ const bool theHasButtons) {
10
StGLWidget::signals.onMouseUnclick.connect(this, &StGLMessageBox::doMouseUnclick);
11
12
myMarginLeft = myRoot->scale(OFFSET_PIXELS);
13
myMarginRight = myRoot->scale(OFFSET_PIXELS);
14
myMarginTop = myRoot->scale(OFFSET_PIXELS);
15
- myMarginBottom = myRoot->scale(24 * 3);
16
+ myMarginBottom = myRoot->scale(theHasButtons ? (24 * 3) : OFFSET_PIXELS);
17
myMinSizeY = myRoot->scale(200);
18
19
int aTitleOffset = myRoot->scale(24);
20
21
myMarginLeft = myRoot->scale(4);
22
myMarginRight = myRoot->scale(4);
23
myMarginTop = myRoot->scale(4);
24
- myMarginBottom = myRoot->scale(32);
25
+ myMarginBottom = myRoot->scale(theHasButtons ? 32 : 4);
26
aTitleOffset = myRoot->scale(4);
27
aBtnBot = -myRoot->scale(4);
28
}
29
30
if(double(aSizeYToFit) / double(aMaxSizeY) > 0.7) {
31
aNewSizeY = stMax(myMinSizeY, aMaxSizeY);
32
}
33
- changeRectPx().bottom() = aNewSizeY;
34
+ changeRectPx().bottom() = getRectPx().top() + aNewSizeY;
35
myContent->changeRectPx().bottom() = myContent->getRectPx().top() + aNewSizeY - myMarginTop - myMarginBottom;
36
}
37
}
38
39
}
40
41
StGLBoxPx aScissorRect;
42
- stglScissorRect(aScissorRect);
43
+ stglScissorRect2d(aScissorRect);
44
aCtx.stglSetScissorRect(aScissorRect, true);
45
46
StGLWidget::stglDraw(theView); // draw children
47
48
49
bool StGLMessageBox::tryUnClick(const StClickEvent& theEvent,
50
bool& theIsItemUnclicked) {
51
+ const bool wasDragged = myContent->hasDragged();
52
if(//isPointIn(StPointD_t(theEvent.PointX, theEvent.PointY)) &&
53
StGLWidget::tryUnClick(theEvent, theIsItemUnclicked)) {
54
theIsItemUnclicked = true;
55
56
- if(myIsContextual) {
57
+ if(myIsContextual && !wasDragged) {
58
myRoot->destroyWithDelay(this);
59
}
60
return true;
61
}
62
63
- if(myIsContextual) {
64
+ if(myIsContextual && !wasDragged) {
65
myRoot->destroyWithDelay(this);
66
}
67
return false;
68
sview-17_04.tar.gz/StGLWidgets/StGLOpenFile.cpp -> sview-20_08.tar.gz/StGLWidgets/StGLOpenFile.cpp
Changed
507
1
2
/**
3
* StGLWidgets, small C++ toolkit for writing GUI using OpenGL.
4
- * Copyright © 2015 Kirill Gavrilov <kirill@sview.ru>
5
+ * Copyright © 2015-2019 Kirill Gavrilov <kirill@sview.ru>
6
*
7
* Distributed under the Boost Software License, Version 1.0.
8
* See accompanying file license-boost.txt or copy at
9
10
11
#include <StGLWidgets/StGLMenu.h>
12
#include <StGLWidgets/StGLMenuItem.h>
13
+#include <StGLWidgets/StGLMenuCheckbox.h>
14
+#include <StGLWidgets/StGLCheckbox.h>
15
#include <StGLWidgets/StGLScrollArea.h>
16
#include <StGLWidgets/StGLTextureButton.h>
17
18
+#include <StThreads/StThread.h>
19
+
20
+#include <fstream>
21
+
22
+#if !defined(_WIN32)
23
+ #include <unistd.h>
24
+#endif
25
+
26
+#ifdef _WIN32
27
+/**
28
+ * Auxiliary tool resolving drive labels.
29
+ */
30
+struct StDriveNameResolver {
31
+
32
+ StMutex Mutex;
33
+ std::vector<StString> Drives;
34
+ std::vector<StString> Labels;
35
+ volatile int NbProcessed;
36
+ volatile bool ToAbort;
37
+
38
+public:
39
+ /**
40
+ * Empty constructor.
41
+ */
42
+ StDriveNameResolver() : NbProcessed(0), ToAbort(false) {}
43
+
44
+ /**
45
+ * Init list.
46
+ */
47
+ void init() {
48
+ const DWORD aLogicalDrivesMask = ::GetLogicalDrives();
49
+ for(int aLetterIter = 'A'; aLetterIter <= 'Z'; ++aLetterIter) {
50
+ const int aBit = 1 << (aLetterIter - 'A');
51
+ if((aLogicalDrivesMask & aBit) != 0) {
52
+ Drives.push_back(StString() + char(aLetterIter) + ":\\");
53
+ Labels.push_back(StString("Drive ") + char(aLetterIter) + ":\\");
54
+ }
55
+ }
56
+
57
+ // enumerate all physical drives seen by Windows
58
+ const GUID PARTITION_BASIC_DATA_GUID = { 0xEBD0A0A2L, 0xB9E5, 0x4433, {0x87, 0xC0, 0x68, 0xB6, 0xB7, 0x26, 0x99, 0xC7} };
59
+ static const DWORD aPartInfoSize = sizeof(DRIVE_LAYOUT_INFORMATION_EX) + 128 * sizeof(PARTITION_INFORMATION_EX); // up to 128 partitions
60
+ char aPartInfoBuffer[aPartInfoSize] = {};
61
+ DRIVE_LAYOUT_INFORMATION_EX* aPartitions = (DRIVE_LAYOUT_INFORMATION_EX* )aPartInfoBuffer;
62
+ for(int aDriveIter = 0; aDriveIter < 1000; ++aDriveIter) {
63
+ const StStringUtfWide aDriveId = StStringUtfWide(L"\\\\.\\PhysicalDrive") + aDriveIter;
64
+ HANDLE aDriveHandle = CreateFileW(aDriveId.toCString(), 0, FILE_SHARE_READ, NULL, OPEN_EXISTING, 0, 0);
65
+ if(aDriveHandle == INVALID_HANDLE_VALUE) {
66
+ break;
67
+ }
68
+
69
+ // list partitions
70
+ DWORD aDummyIor = 0;
71
+ if(!DeviceIoControl(aDriveHandle, IOCTL_DISK_GET_DRIVE_LAYOUT_EX, NULL, 0, aPartitions, aPartInfoSize, &aDummyIor, NULL)) {
72
+ CloseHandle(aDriveHandle);
73
+ continue;
74
+ }
75
+
76
+ for(DWORD aPartIter = 0; aPartIter < aPartitions->PartitionCount; ++aPartIter) {
77
+ const PARTITION_INFORMATION_EX& aPart = aPartitions->PartitionEntry[aPartIter];
78
+ switch(aPart.PartitionStyle) {
79
+ case PARTITION_STYLE_MBR: {
80
+ if(aPart.Mbr.PartitionType == PARTITION_ENTRY_UNUSED || !aPart.Mbr.RecognizedPartition) {
81
+ continue; // ignore unused
82
+ }
83
+ break;
84
+ }
85
+ case PARTITION_STYLE_GPT: {
86
+ if(aPart.Gpt.PartitionType != PARTITION_BASIC_DATA_GUID) {
87
+ continue; // ignore unused
88
+ }
89
+ break;
90
+ }
91
+ default: {
92
+ continue; // ignore unknown
93
+ }
94
+ }
95
+
96
+ const StStringUtfWide aPartVolume = findPartitionVolume(aDriveIter, aPart);
97
+ if(aPartVolume.isEmpty()) {
98
+ continue;
99
+ }
100
+
101
+ // find mount points
102
+ DWORD aMntPointLen = 0;
103
+ std::vector<wchar_t> aMntPoints(1);
104
+ GetVolumePathNamesForVolumeNameW(aPartVolume.toCString(), aMntPoints.data(), 0, &aMntPointLen);
105
+ if(aMntPointLen > 0) {
106
+ aMntPoints.resize (aMntPointLen + 1, '\0');
107
+ if(GetVolumePathNamesForVolumeNameW(aPartVolume.toCString(), aMntPoints.data(), aMntPointLen, &aMntPointLen) != FALSE) {
108
+ StString aMntPointRes(aMntPoints.data());
109
+ for(const wchar_t* aMntPointIter = aMntPoints.data(); aMntPointIter[0] != '\0'; aMntPointIter += wcslen(aMntPointIter)) {
110
+ const StString aMntPoint(aMntPointIter);
111
+ if(aMntPoint.getLength() == 3
112
+ && aMntPoint.toCString()[1] == ':'
113
+ && aMntPoint.toCString()[2] == '\\') {
114
+ // filter common logical drive letter
115
+ aMntPointRes.clear();
116
+ break;
117
+ }
118
+ }
119
+ if(!aMntPointRes.isEmpty()) {
120
+ if(aMntPointRes.getLength() > 3
121
+ && aMntPointRes.isEndsWith('\\')) {
122
+ aMntPointRes = aMntPointRes.subString(0, aMntPointRes.getLength() - 1);
123
+ }
124
+ Drives.push_back(aMntPointRes);
125
+ Labels.push_back(StString("Drive ") + aMntPointRes);
126
+ }
127
+ }
128
+ }
129
+ }
130
+ CloseHandle(aDriveHandle);
131
+ }
132
+ }
133
+
134
+ /**
135
+ * Working thread callback.
136
+ */
137
+ void resolve() {
138
+ wchar_t aVolumeName[256];
139
+ wchar_t aFileSystemName[256];
140
+ StString aDriveLabel;
141
+ const StString aDriveA = "A:";
142
+ const StString aDriveB = "B:";
143
+ for(; NbProcessed < (int )Drives.size(); StAtomicOp::Increment(NbProcessed)) {
144
+ const StString& aDrivePath = Drives[NbProcessed];
145
+ StStringUtfWide aDrivePathW = aDrivePath.toUtfWide();
146
+ if(!aDrivePath.isEndsWith('\\')) {
147
+ aDrivePathW += '\\';
148
+ }
149
+ DWORD aSerialNumber = 0, aMaxFileNameLength = 0, aFileSystemFlags = 0;
150
+ if(!aDrivePath.isStartsWithIgnoreCase(aDriveA)
151
+ && !aDrivePath.isStartsWithIgnoreCase(aDriveB)
152
+ && ::GetVolumeInformationW(aDrivePathW.toCString(),
153
+ aVolumeName, sizeof(aVolumeName) / sizeof(wchar_t),
154
+ &aSerialNumber, &aMaxFileNameLength, &aFileSystemFlags,
155
+ aFileSystemName, sizeof(aFileSystemName) / sizeof(wchar_t))) {
156
+ aDriveLabel.fromUnicode(aVolumeName);
157
+ if(!aDriveLabel.isEmpty() && !ToAbort) {
158
+ StMutexAuto aLock(Mutex);
159
+ Labels[NbProcessed] = aDrivePath + " [" + aDriveLabel + "]";
160
+ }
161
+ }
162
+
163
+ if(ToAbort) {
164
+ return;
165
+ }
166
+ }
167
+ }
168
+
169
+ /**
170
+ * Working thread callback.
171
+ */
172
+ static SV_THREAD_FUNCTION resolveThread(void* thePtr) {
173
+ StHandle<StDriveNameResolver> aThis = *static_cast<StHandle<StDriveNameResolver>* >(thePtr);
174
+ aThis->resolve();
175
+ return SV_THREAD_RETURN 0;
176
+ }
177
+
178
+ private:
179
+
180
+ /**
181
+ * Find volume name for partition.
182
+ */
183
+ static StStringUtfWide findPartitionVolume(DWORD theDiskNumber, const PARTITION_INFORMATION_EX& thePart) {
184
+ // handle up-to 256 extents
185
+ static const DWORD THE_EXTENTS_SIZE = sizeof(VOLUME_DISK_EXTENTS) + 256 * sizeof(DISK_EXTENT);
186
+ char aBuffer[THE_EXTENTS_SIZE] = {};
187
+ VOLUME_DISK_EXTENTS* aVolDiskExtents = (VOLUME_DISK_EXTENTS* )aBuffer;
188
+
189
+ std::vector<wchar_t> aVolName(4096, '\0');
190
+ HANDLE aVolIter = FindFirstVolumeW(aVolName.data(), (DWORD )aVolName.size());
191
+ for(bool hasMoreVolumes = aVolIter != INVALID_HANDLE_VALUE; hasMoreVolumes; hasMoreVolumes = FindNextVolumeW (aVolIter, aVolName.data(), (DWORD )aVolName.size()) != FALSE) {
192
+ aVolName[wcslen(aVolName.data()) - 1] = '\0'; // volume must be without trailing backslash here
193
+ HANDLE aVolHandle = CreateFileW(aVolName.data(), 0, FILE_SHARE_READ, NULL, OPEN_EXISTING, 0, 0);
194
+ aVolName[wcslen(aVolName.data())] = '\\';
195
+ if(aVolHandle == INVALID_HANDLE_VALUE) {
196
+ continue;
197
+ }
198
+
199
+ DWORD anExtentsSize = 0;
200
+ if(DeviceIoControl(aVolHandle, IOCTL_VOLUME_GET_VOLUME_DISK_EXTENTS, NULL, 0, (void* )aVolDiskExtents, THE_EXTENTS_SIZE, &anExtentsSize, NULL) == FALSE) {
201
+ CloseHandle(aVolHandle);
202
+ continue;
203
+ }
204
+
205
+ for(DWORD anExtentIter = 0; anExtentIter < aVolDiskExtents->NumberOfDiskExtents; ++anExtentIter) {
206
+ const DISK_EXTENT& anExtent = aVolDiskExtents->Extents[anExtentIter];
207
+ if(anExtent.DiskNumber == theDiskNumber
208
+ && anExtent.StartingOffset.QuadPart == thePart.StartingOffset.QuadPart
209
+ && anExtent.ExtentLength.QuadPart == thePart.PartitionLength.QuadPart) {
210
+ CloseHandle(aVolHandle);
211
+ FindVolumeClose(aVolIter);
212
+ return StStringUtfWide(aVolName.data());
213
+ }
214
+ }
215
+ CloseHandle(aVolHandle);
216
+ }
217
+ FindVolumeClose(aVolIter);
218
+ return StStringUtfWide();
219
+ }
220
+
221
+};
222
+#endif
223
+
224
+/**
225
+ * Dummy sub-class overriding scrollable behavior.
226
+ */
227
+class StGLOpenFileMenu : public StGLMenu {
228
+
229
+ public:
230
+
231
+ ST_LOCAL StGLOpenFileMenu(StGLWidget* theParent,
232
+ int theLeft,
233
+ int theTop,
234
+ int theOrient = MENU_VERTICAL,
235
+ bool theIsRootMenu = false)
236
+ : StGLMenu(theParent, theLeft, theTop, theOrient, theIsRootMenu) {}
237
+
238
+ ST_LOCAL virtual bool doScroll(const StScrollEvent& theEvent) ST_ATTR_OVERRIDE {
239
+ return StGLWidget::doScroll(theEvent); // skip StGLMenu
240
+ }
241
+
242
+};
243
+
244
StGLOpenFile::StGLOpenFile(StGLWidget* theParent,
245
const StString& theTitle,
246
const StString& theCloseText)
247
: StGLMessageBox(theParent, theTitle, "",
248
theParent->getRoot()->scale(512), theParent->getRoot()->scale(400)),
249
myCurrentPath(NULL),
250
+ myHotListContent(NULL),
251
myHotList(NULL),
252
myList(NULL),
253
+ myMainFilterCheck(NULL),
254
+ myExtraFilterCheck(NULL),
255
+ myToShowMainFilter(new StBoolParam(true)),
256
+ myToShowExtraFilter(new StBoolParam(false)),
257
myHighlightColor(0.5f, 0.5f, 0.5f, 1.0f),
258
myItemColor (1.0f, 1.0f, 1.0f, 1.0f),
259
myFileColor (0.7f, 0.7f, 0.7f, 1.0f),
260
261
myIconSizeX(theParent->getRoot()->scale(16)) {
262
myToAdjustY = false;
263
264
+ myToShowMainFilter ->signals.onChanged = stSlot(this, &StGLOpenFile::doFilterCheck);
265
+ myToShowExtraFilter->signals.onChanged = stSlot(this, &StGLOpenFile::doFilterCheck);
266
+
267
int aMarginTop = myMarginTop + myRoot->scale(30);
268
myCurrentPath = new StGLTextArea(this, myMarginLeft, myMarginTop, StGLCorner(ST_VCORNER_TOP, ST_HCORNER_LEFT),
269
myContent->getRectPx().width(), myContent->getRectPx().height());
270
271
StGLTextFormatter::ST_ALIGN_Y_TOP);
272
myCurrentPath->setTextColor(myRoot->getColorForElement(StGLRootWidget::Color_MessageText));
273
274
- myHotList = new StGLMenu(this, 0, 0, StGLMenu::MENU_VERTICAL_COMPACT);
275
+ myContent->changeRectPx().top() = aMarginTop;
276
+ myContent->changeRectPx().left() = myMarginLeft + myHotSizeX;
277
+
278
+ myHotListContent = new StGLScrollArea(this, myMarginLeft, aMarginTop,
279
+ StGLCorner(ST_VCORNER_TOP, ST_HCORNER_LEFT),
280
+ myHotSizeX, myContent->getRectPx().height());
281
+
282
+ myHotList = new StGLOpenFileMenu(myHotListContent, 0, 0, StGLMenu::MENU_VERTICAL_COMPACT);
283
myHotList->setOpacity(1.0f, true);
284
myHotList->setItemWidth(myHotSizeX);
285
myHotList->setColor(StGLVec4(0.0f, 0.0f, 0.0f, 0.0f));
286
- myHotList->changeRectPx().top() = aMarginTop;
287
- myHotList->changeRectPx().left() = myMarginLeft;
288
- myHotList->changeRectPx().right() = myMarginLeft + myHotSizeX;
289
- myContent->changeRectPx().top() = aMarginTop;
290
- myContent->changeRectPx().left() = myMarginLeft + myHotSizeX;
291
292
- myList = new StGLMenu(myContent, 0, 0, StGLMenu::MENU_VERTICAL_COMPACT);
293
+ myList = new StGLOpenFileMenu(myContent, 0, 0, StGLMenu::MENU_VERTICAL_COMPACT);
294
myList->setOpacity(1.0f, true);
295
myList->setColor(StGLVec4(0.0f, 0.0f, 0.0f, 0.0f));
296
myList->setItemWidthMin(myContent->getRectPx().width());
297
298
//if(!myRoot->isMobile()) {
299
addButton(theCloseText);
300
//}
301
+
302
+ addSystemDrives();
303
+}
304
+
305
+void StGLOpenFile::addSystemDrives() {
306
+#ifdef _WIN32
307
+ StHandle<StDriveNameResolver> aResolver = new StDriveNameResolver();
308
+ aResolver->init();
309
+ if(!aResolver->Drives.empty()) {
310
+ // name resolver might hang on resource unavailability
311
+ StThread aThread(StDriveNameResolver::resolveThread, &aResolver);
312
+ if(!aThread.wait(1000)) {
313
+ //aThread.kill();
314
+ aResolver->ToAbort = true;
315
+ aThread.detach();
316
+ }
317
+
318
+ StMutexAuto aLock(aResolver->Mutex);
319
+ for(size_t aDriveIter = 0; aDriveIter < aResolver->Drives.size(); ++aDriveIter) {
320
+ addHotItem(aResolver->Drives[aDriveIter], aResolver->Labels[aDriveIter]);
321
+ }
322
+ }
323
+#else
324
+ // modern Android does not permit listing / content
325
+ if(access("/", R_OK) == 0) {
326
+ addHotItem("/", "Root");
327
+ }
328
+#endif
329
+
330
+#if defined(__ANDROID__)
331
+ std::ifstream aMountsFile("/proc/mounts");
332
+ if(!aMountsFile.is_open()) {
333
+ return;
334
+ }
335
+ std::string aLineStd;
336
+ while(std::getline(aMountsFile, aLineStd)) {
337
+ const StString aLine(aLineStd.c_str());
338
+ StHandle<StArrayList<StString> > aMountLine = aLine.split(' ');
339
+ if(aMountLine->size() < 4) {
340
+ continue;
341
+ }
342
+
343
+ const StString& aDevice = aMountLine->getValue(0);
344
+ const StString& aMount = aMountLine->getValue(1);
345
+ const StString& aFileSys = aMountLine->getValue(2);
346
+ const StString aMountLower = aMount.lowerCased();
347
+ // filter by unsupported file-system
348
+ /*if(aFileSys == stCString("tmpfs")
349
+ || aFileSys == stCString("devpts")
350
+ || aFileSys == stCString("sysfs")
351
+ || aFileSys == stCString("selinuxfs")
352
+ || aFileSys == stCString("debugfs")
353
+ || aFileSys == stCString("configfs")
354
+ || aFileSys == stCString("cgroup")
355
+ || aFileSys == stCString("functionfs")) {
356
+ continue;
357
+ }*/
358
+ // filter by supported file-system
359
+ if(aFileSys != stCString("fuse")
360
+ && aFileSys != stCString("vfat")
361
+ && aFileSys != stCString("ntfs")
362
+ && aFileSys != stCString("ext4")) {
363
+ continue;
364
+ }
365
+ // filter special paths
366
+ if(aMountLower.isStartsWith(stCString("/mnt/secure"))
367
+ || aMountLower.isStartsWith(stCString("/mnt/asec"))
368
+ || aMountLower.isStartsWith(stCString("/mnt/mapper"))
369
+ || aMountLower.isStartsWith(stCString("/mnt/obb"))
370
+ || aMountLower == stCString("/storage/emulated")
371
+ || aMountLower.isStartsWith(stCString("/mnt/shell/emulated")) // ignore symlink to /storage/emulated/0/ for current user, Android 4.2+
372
+ || aMountLower.isStartsWith(stCString("/storage/emulated/legacy"))) { // ignore symlink to /storage/emulated/X/ for current user
373
+ continue;
374
+ }
375
+ // filter bootdevice entities
376
+ if( aDevice.isStartsWith(stCString("/dev/block"))
377
+ && !aDevice.isStartsWith(stCString("/dev/block/vold"))) {
378
+ continue;
379
+ }
380
+ addHotItem(aMount);
381
+ }
382
+#endif
383
}
384
385
StGLOpenFile::~StGLOpenFile() {
386
387
}
388
}
389
390
-void StGLOpenFile::setMimeList(const StMIMEList& theFilter) {
391
- myFilter = theFilter;
392
- myExtensions = theFilter.getExtensionsList();
393
+void StGLOpenFile::setMimeList(const StMIMEList& theFilter,
394
+ const StString& theName,
395
+ const bool theIsExtra) {
396
+ if(theIsExtra) {
397
+ myExtraFilter = theFilter;
398
+ } else {
399
+ myFilter = theFilter;
400
+ }
401
+
402
+ StGLMenuCheckbox*& aFilterWidget = theIsExtra ? myExtraFilterCheck : myMainFilterCheck;
403
+ if(!theName.isEmpty() && aFilterWidget == NULL) {
404
+ StHandle<StBoolParam>& aFilterParam = theIsExtra ? myToShowExtraFilter : myToShowMainFilter;
405
+ aFilterWidget = addHotCheckbox(aFilterParam, theName);
406
+ }
407
+ if(aFilterWidget != NULL) {
408
+ aFilterWidget->setText(theName);
409
+ }
410
+ initExtensions();
411
+}
412
+
413
+StGLMenuCheckbox* StGLOpenFile::addHotCheckbox(const StHandle<StBoolParam>& theParam,
414
+ const StString& theName) {
415
+ StGLMenuCheckbox* aFilterWidget = new StGLMenuCheckbox(myHotList, theParam);
416
+
417
+ StGLCheckbox* aCheckBox = aFilterWidget->getCheckbox();
418
+ aCheckBox->setColor(myHotColor);
419
+ aCheckBox->setCorner(StGLCorner(ST_VCORNER_CENTER, ST_HCORNER_RIGHT));
420
+ aCheckBox->changeRectPx().moveLeftTo(-aCheckBox->getRectPx().left());
421
+
422
+ aFilterWidget->changeMargins().left = -(myMarginX + myIconSizeX + myMarginX); // TODO weird logic
423
+ aFilterWidget->setupStyle(StFTFont::Style_Italic);
424
+ aFilterWidget->setText(theName);
425
+ aFilterWidget->setupAlignment(StGLTextFormatter::ST_ALIGN_X_RIGHT, StGLTextFormatter::ST_ALIGN_Y_CENTER);
426
+ aFilterWidget->setTextColor(myHotColor);
427
+ aFilterWidget->setHilightColor(myHighlightColor);
428
+ return aFilterWidget;
429
+}
430
+
431
+void StGLOpenFile::initExtensions() {
432
+ myExtensions.clear();
433
+ StArrayList<StString> aList1 = myToShowMainFilter ->getValue() ? myFilter.getExtensionsList() : StArrayList<StString>(1);
434
+ StArrayList<StString> aList2 = myToShowExtraFilter->getValue() ? myExtraFilter.getExtensionsList() : StArrayList<StString>(1);
435
+ size_t anExtent = aList1.size() + aList2.size();
436
+ myExtensions.initList(anExtent);
437
+ for(size_t anExtIter = 0; anExtIter < aList1.size(); ++anExtIter) {
438
+ myExtensions.add(aList1[anExtIter]);
439
+ }
440
+ for(size_t anExtIter = 0; anExtIter < aList2.size(); ++anExtIter) {
441
+ myExtensions.add(aList2[anExtIter]);
442
+ }
443
}
444
445
void StGLOpenFile::doHotItemClick(const size_t theItemId) {
446
myItemToLoad = myHotPaths[theItemId];
447
}
448
449
+void StGLOpenFile::doFilterCheck(const bool ) {
450
+ initExtensions();
451
+ if(!myFolder.isNull()) {
452
+ StString aPath = myFolder->getPath();
453
+ openFolder(aPath);
454
+ }
455
+}
456
+
457
void StGLOpenFile::doFileItemClick(const size_t theItemId) {
458
const StFileNode* aNode = myFolder->getValue(theItemId);
459
myItemToLoad = aNode->getPath();
460
461
myItemToLoad.clear();
462
if(StFolder::isFolder(aPath)) {
463
openFolder(aPath);
464
- } else {
465
+ } else if(StFileNode::isFileExists(aPath)) {
466
StHandle<StString> aPathHandle = new StString(aPath);
467
signals.onFileSelected.emit(aPathHandle);
468
myRoot->destroyWithDelay(this);
469
+ } else {
470
+ StGLMessageBox* aMsgBox = new StGLMessageBox(myRoot, "Error", StString("Path is inaccessible!\n") + aPath);
471
+ aMsgBox->addButton("Close");
472
+ aMsgBox->stglInit();
473
}
474
}
475
return aRes;
476
477
478
StGLMenuItem* anItem = new StGLPassiveMenuItem(myHotList);
479
setItemIcon(anItem, myHotColor, true);
480
+ anItem->setupStyle(StFTFont::Style_Bold);
481
anItem->setText(aName);
482
anItem->setTextColor(myHotColor);
483
anItem->setHilightColor(myHighlightColor);
484
485
int aSizeX = anItem->getMargins().left + anItem->computeTextWidth() + anItem->getMargins().right;
486
myHotSizeX = stMax(myHotSizeX, aSizeX);
487
488
- myContent->changeRectPx().left() = myMarginLeft + myHotSizeX;
489
+ myHotListContent->changeRectPx().right() = myHotListContent->getRectPx().left() + myHotSizeX;
490
+ if(myMainFilterCheck != NULL) {
491
+ myMainFilterCheck->changeRectPx().right() = myHotSizeX;
492
+ }
493
+ myContent->changeRectPx().left() = myHotListContent->getRectPx().right();
494
myList->setItemWidthMin(myContent->getRectPx().width());
495
}
496
497
498
myFolder = new StFolder(aFolder);
499
myFolder->init(myExtensions, 1, true);
500
StString aPath = myFolder->getPath();
501
- myCurrentPath->setText(StString("<b>Location:*</b>") + aPath + (!aPath.isEmpty() ? ST_FILE_SPLITTER : ""));
502
+ myCurrentPath->setText(StString("<b>Location:*</b>") + aPath
503
+ + (!aPath.isEmpty() && !aPath.isEndsWith(SYS_FS_SPLITTER) ? ST_FILE_SPLITTER : ""));
504
505
StString aPathUp = StFileNode::getFolderUp(aPath);
506
if(!aPathUp.isEmpty()) {
507
sview-17_04.tar.gz/StGLWidgets/StGLPlayList.cpp -> sview-20_08.tar.gz/StGLWidgets/StGLPlayList.cpp
Changed
10
1
2
3
StGLContext& aCtx = getContext();
4
StGLBoxPx aScissorRect;
5
- stglScissorRect(aScissorRect);
6
+ stglScissorRect2d(aScissorRect);
7
aCtx.stglSetScissorRect(aScissorRect, true);
8
9
StGLWidget::stglDraw(theView);
10
sview-17_04.tar.gz/StGLWidgets/StGLRootWidget.cpp -> sview-20_08.tar.gz/StGLWidgets/StGLRootWidget.cpp
Changed
101
1
2
/**
3
* StGLWidgets, small C++ toolkit for writing GUI using OpenGL.
4
- * Copyright © 2009-2017 Kirill Gavrilov <kirill@sview.ru>
5
+ * Copyright © 2009-2020 Kirill Gavrilov <kirill@sview.ru>
6
*
7
* Distributed under the Boost Software License, Version 1.0.
8
* See accompanying file license-boost.txt or copy at
9
10
myGlCtx->stglSyncState();
11
myGlCtx->core20fwd->glGetIntegerv(GL_VIEWPORT, myViewport); // cache viewport
12
13
- switch(theView) {
14
- case ST_DRAW_LEFT:
15
- myScrDispX = myLensDist * GLfloat(0.5 * myRectGl.width());
16
- myScrDispXPx = int(double(myLensDist) * 0.5 * double(myRectPxFull.width()));
17
- break;
18
- case ST_DRAW_RIGHT:
19
- myScrDispX = -myLensDist * GLfloat(0.5 * myRectGl.width());
20
- myScrDispXPx = -int(double(myLensDist) * 0.5 * double(myRectPxFull.width()));
21
- break;
22
- case ST_DRAW_MONO:
23
- default:
24
- myScrDispX = 0.0f;
25
- myScrDispXPx = 0;
26
- break;
27
- }
28
-
29
- if(myTextProgram->isValid()) {
30
- myTextProgram->use(*myGlCtx);
31
- myTextProgram->setProjMat(*myGlCtx, myProjCamera.getProjMatrix());
32
- myTextProgram->unuse(*myGlCtx);
33
- }
34
- if(myTextBorderProgram->isValid()) {
35
- myTextBorderProgram->use(*myGlCtx);
36
- myTextBorderProgram->setProjMat(*myGlCtx, myProjCamera.getProjMatrix());
37
- myTextBorderProgram->unuse(*myGlCtx);
38
+ myScrDispX = 0.0f;
39
+ myScrDispXPx = 0;
40
+ if(theView == ST_DRAW_LEFT || theView == ST_DRAW_RIGHT) {
41
+ if(myProjCamera.isCustomProjection()) {
42
+ StGLVec4 aTestProj = myProjCamera.getProjMatrix() * StGLVec4(0, 0, myProjCamera.getZScreen(), 1.0f);
43
+ aTestProj /= aTestProj.w();
44
+ aTestProj.x() = 0.5f + aTestProj.x() * 0.5f;
45
+ aTestProj.y() = 0.5f + aTestProj.y() * 0.5f;
46
+
47
+ myScrDispX = float((aTestProj.x() - 0.5f) * myRectGl.width());
48
+ myScrDispXPx = int(double(aTestProj.x()) * double(myViewport[2]) - double(myViewport[2])/2);
49
+ //myScrDispYPx = int(double(aTestProj.y()) * double(myViewport[3]) - double(myViewport[3])/2);
50
+ } else {
51
+ if(theView == ST_DRAW_LEFT) {
52
+ myScrDispX = myLensDist * float(0.5 * myRectGl.width());
53
+ myScrDispXPx = int(double(myLensDist) * 0.5 * double(myViewport[2]));
54
+ } else {
55
+ myScrDispX = -myLensDist * float(0.5 * myRectGl.width());
56
+ myScrDispXPx = -int(double(myLensDist) * 0.5 * double(myViewport[2]));
57
+ }
58
+ }
59
}
60
61
StGLWidget::stglDraw(theView);
62
63
StGLWidget::stglUpdate(theCursorZo, theIsPreciseInput);
64
}
65
66
-void StGLRootWidget::stglScissorRect(const StRectI_t& theRect,
67
- StGLBoxPx& theScissorRect) const {
68
+void StGLRootWidget::stglScissorRectInternal(const StRectI_t& theRect,
69
+ const bool theIs2d,
70
+ StGLBoxPx& theScissorRect) const {
71
const GLint aVPortWidth = myViewport[2];
72
const GLint aVPortHeight = myViewport[3];
73
const GLint aRootWidth = myRectPxFull.width();
74
75
const GLdouble aWidthFactor = GLdouble(aVPortWidth) / GLdouble(aRootWidth);
76
const GLdouble aHeightFactor = GLdouble(aVPortHeight) / GLdouble(aRootHeight);
77
78
- theScissorRect.x() = myViewport[0] + GLint(aWidthFactor * GLdouble(theRect.left() + myScrDispXPx));
79
+ const int anEyeShiftPx = theIs2d ? myScrDispXPx : 0;
80
+ theScissorRect.x() = myViewport[0] + GLint(aWidthFactor * GLdouble(theRect.left() + anEyeShiftPx));
81
theScissorRect.y() = myViewport[1] + GLint(aHeightFactor * GLdouble(aRootHeight - theRect.bottom()));
82
83
theScissorRect.width() = GLint(aWidthFactor * GLdouble(theRect.width()));
84
85
myMenuProgram->setProjMat(*myGlCtx, getScreenProjection());
86
myMenuProgram->unuse(*myGlCtx);
87
}
88
+ if(myTextProgram->isValid()) {
89
+ myTextProgram->use(*myGlCtx);
90
+ myTextProgram->setProjMat(*myGlCtx, getScreenProjection());
91
+ myTextProgram->unuse(*myGlCtx);
92
+ }
93
+ if(myTextBorderProgram->isValid()) {
94
+ myTextBorderProgram->use(*myGlCtx);
95
+ myTextBorderProgram->setProjMat(*myGlCtx, getScreenProjection());
96
+ myTextBorderProgram->unuse(*myGlCtx);
97
+ }
98
99
// update all child widgets
100
if(isChanged) {
101
sview-17_04.tar.gz/StGLWidgets/StGLScrollArea.cpp -> sview-20_08.tar.gz/StGLWidgets/StGLScrollArea.cpp
Changed
63
1
2
myDragYCumul(0),
3
myFlingAccel((double )myRoot->scale(200)),
4
myFlingYSpeed(0.0),
5
- myFlingYDone(0) {
6
+ myFlingYDone(0),
7
+ myScrollYAccum(0.0f) {
8
//
9
}
10
11
12
}
13
14
StGLBoxPx aScissorRect;
15
- stglScissorRect(aScissorRect);
16
+ stglScissorRect2d(aScissorRect);
17
aCtx.stglSetScissorRect(aScissorRect, true);
18
19
StGLWidget::stglDraw(theView); // draw children
20
21
22
bool StGLScrollArea::tryUnClick(const StClickEvent& theEvent,
23
bool& theIsItemUnclicked) {
24
+ bool toCancel = false;
25
if(myIsLeftClick
26
&& theEvent.Button == ST_MOUSE_LEFT) {
27
+ if(myHasDragged) {
28
+ toCancel = true;
29
+ }
30
myIsLeftClick = false;
31
myHasDragged = false;
32
if(myDragTimer.isOn()) {
33
34
}
35
}
36
}
37
+ if(toCancel) {
38
+ StClickEvent anEvent = theEvent;
39
+ anEvent.Type = stEvent_MouseCancel;
40
+ return StGLWidget::tryUnClick(anEvent, theIsItemUnclicked);
41
+ }
42
return StGLWidget::tryUnClick(theEvent, theIsItemUnclicked);
43
}
44
45
46
return true;
47
}
48
49
- int aDeltaY = (int )fabs(theEvent.DeltaY * 2.0f);
50
- if(theEvent.DeltaY > 0.001f) {
51
- doScroll( myRoot->scale(aDeltaY));
52
- } else if(theEvent.DeltaY < -0.001f) {
53
- doScroll(-myRoot->scale(aDeltaY));
54
+ myScrollYAccum += theEvent.DeltaY * 20.0f;
55
+ const int aDeltaY = (int )myScrollYAccum;
56
+ if(aDeltaY != 0) {
57
+ myScrollYAccum -= float(aDeltaY);
58
+ const int aDeltaScaled = myRoot->scale(std::abs(aDeltaY));
59
+ doScroll(aDeltaY > 0 ? aDeltaScaled : -aDeltaScaled);
60
}
61
return true;
62
}
63
sview-17_04.tar.gz/StGLWidgets/StGLSeekBar.cpp -> sview-20_08.tar.gz/StGLWidgets/StGLSeekBar.cpp
Changed
59
1
2
return;
3
}
4
5
- const double aPos = stMin(stMax(getPointInEx(theCursor), 0.0), 1.0);
6
- const int aPosPx = int(aPos * double(getRectPx().width()));
7
-
8
+ const int aRoundTol = myRoot->scale(1);
9
+ const int aMaxPosPx = getRectPx().width();
10
+ double aPos = stMin(stMax(getPointInEx(theCursor), 0.0), 1.0);
11
+ int aPosPx = int(aPos * double(aMaxPosPx));
12
const int aMoveTolerPx = myMoveTolerPx > 0 ? myMoveTolerPx : myRoot->scale(theIsPreciseInput ? 1 : 2);
13
- if(myClickPos >= 0
14
- && std::abs(aPosPx - myClickPos) < aMoveTolerPx) {
15
- return;
16
+ if(std::abs(aPosPx - 0) <= aRoundTol) {
17
+ aPos = 0.0;
18
+ aPosPx = 0;
19
+ } else if(std::abs(aPosPx - aMaxPosPx) <= aRoundTol) {
20
+ aPos = 1.0;
21
+ aPosPx = aMaxPosPx;
22
+ }
23
+
24
+ if(myClickPos >= 0) {
25
+ if(myClickPos == aPosPx) {
26
+ return;
27
+ }
28
+
29
+ if(aPosPx != 0
30
+ && aPosPx != aMaxPosPx
31
+ && std::abs(aPosPx - myClickPos) < aMoveTolerPx) {
32
+ return;
33
+ }
34
}
35
36
myClickPos = aPosPx;
37
38
}
39
40
void StGLSeekBar::doMouseUnclick(const int mouseBtn) {
41
- const double aPos = stMin(stMax(getPointInEx(myRoot->getCursorZo()), 0.0), 1.0);
42
- const int aTolerance = myRoot->scale(1);
43
- const int aPosPx = int(aPos * double(getRectPx().width()));
44
+ const int aTolerance = myRoot->scale(1);
45
+ const int aMaxPosPx = getRectPx().width();
46
+ double aPos = stMin(stMax(getPointInEx(myRoot->getCursorZo()), 0.0), 1.0);
47
+ int aPosPx = int(aPos * double(aMaxPosPx));
48
+ if(std::abs(aPosPx - 0) <= aTolerance) {
49
+ aPos = 0.0;
50
+ aPosPx = 0;
51
+ } else if(std::abs(aPosPx - aMaxPosPx) <= aTolerance) {
52
+ aPos = 1.0;
53
+ aPosPx = aMaxPosPx;
54
+ }
55
+
56
if(myClickPos >= 0
57
&& std::abs(aPosPx - myClickPos) < aTolerance) {
58
myClickPos = -1;
59
sview-17_04.tar.gz/StGLWidgets/StGLSubtitles.cpp -> sview-20_08.tar.gz/StGLWidgets/StGLSubtitles.cpp
Changed
313
1
2
/**
3
* StGLWidgets, small C++ toolkit for writing GUI using OpenGL.
4
- * Copyright © 2010-2015 Kirill Gavrilov <kirill@sview.ru>
5
+ * Copyright © 2010-2020 Kirill Gavrilov <kirill@sview.ru>
6
*
7
* Distributed under the Boost Software License, Version 1.0.
8
* See accompanying file license-boost.txt or copy at
9
10
11
#include <StGLCore/StGLCore20.h>
12
#include <StGL/StGLProgram.h>
13
+#include <StGLWidgets/StGLImageRegion.h>
14
#include <StGLWidgets/StGLRootWidget.h>
15
16
namespace {
17
static const size_t SHARE_IMAGE_PROGRAM_ID = StGLRootWidget::generateShareId();
18
+ static StGLVCorner parseCorner(int theVal) { return (StGLVCorner )theVal; }
19
}
20
21
class StGLSubtitles::StImgProgram : public StGLProgram {
22
23
};
24
25
StGLSubtitles::StSubShowItems::StSubShowItems()
26
-: StArrayList<StHandle <StSubItem> >(8) {
27
+: StArrayList<StHandle <StSubItem> >(8), Scale (1.0f) {
28
//
29
}
30
31
32
const StImagePlane& anImage = getFirst()->Image;
33
if(!anImage.isNull()) {
34
Image.initCopy(anImage, false);
35
+ Scale = getFirst()->Scale;
36
} else {
37
Image.nullify();
38
+ Scale = 1.0f;
39
}
40
41
return isChanged;
42
43
const StImagePlane& anImage = theItem->Image;
44
if(!anImage.isNull()) {
45
Image.initCopy(anImage, false);
46
+ Scale = theItem->Scale;
47
}
48
49
StArrayList<StHandle <StSubItem> >::add(theItem);
50
}
51
52
-inline StGLVCorner parseCorner(int theVal) {
53
- return (StGLVCorner )theVal;
54
-}
55
-
56
-StGLSubtitles::StGLSubtitles(StGLWidget* theParent,
57
+StGLSubtitles::StGLSubtitles(StGLImageRegion* theParent,
58
const StHandle<StSubQueue>& theSubQueue,
59
const StHandle<StInt32Param>& thePlace,
60
- const StHandle<StFloat32Param>& theTopDY,
61
- const StHandle<StFloat32Param>& theBottomDY,
62
- const StHandle<StFloat32Param>& theFontSize,
63
- const StHandle<StFloat32Param>& theParallax,
64
- const StHandle<StEnumParam>& theParser)
65
+ const StHandle<StFloat32Param>& theFontSize)
66
: StGLTextArea(theParent,
67
0, 0,
68
StGLCorner(parseCorner(thePlace->getValue()), ST_HCORNER_CENTER),
69
theParent->getRoot()->scale(800), theParent->getRoot()->scale(160)),
70
- myPlace(thePlace),
71
- myTopDY(theTopDY),
72
- myBottomDY(theBottomDY),
73
- myFontSize(theFontSize),
74
- myParallax(theParallax),
75
- myParser(theParser),
76
myQueue(theSubQueue),
77
myPTS(0.0),
78
myImgProgram(getRoot()->getShare(SHARE_IMAGE_PROGRAM_ID)) {
79
+ params.Place = thePlace;
80
+ params.FontSize = theFontSize;
81
+ params.TopDY = new StFloat32Param(100.0f);
82
+ params.BottomDY = new StFloat32Param(100.0f);
83
+ params.Parallax = new StFloat32Param(0.0f);
84
+ params.Parser = new StEnumParam(1, stCString("subsParser"));
85
+ params.ToApplyStereo = new StBoolParamNamed(true, stCString("subsApplyStereo"));
86
+
87
if(myQueue.isNull()) {
88
myQueue = new StSubQueue();
89
}
90
91
92
StHandle<StGLFont> aFontNew = new StGLFont();
93
StHandle<StFTLibrary> aLib = getRoot()->getFontManager()->getLibraty();
94
- const FontSize aSize = (FontSize )(int )myFontSize->getValue();
95
+ const FontSize aSize = (FontSize )(int )params.FontSize->getValue();
96
const unsigned int aResolution = getRoot()->getFontManager()->getResolution();
97
for(size_t anIter = 0; anIter < StFTFont::SubsetsNB; ++anIter) {
98
StHandle<StGLFontEntry>& aFontGlSrc = myFont->changeFont((StFTFont::Subset )anIter);
99
100
101
StHandle<StFTFont> aFontFt = new StFTFont(aLib);
102
for(int aStyleIt = 0; aStyleIt < StFTFont::StylesNB; ++aStyleIt) {
103
- aFontFt->load(aFontGlSrc->getFont()->getFilePath((StFTFont::Style )aStyleIt), (StFTFont::Style )aStyleIt);
104
+ aFontFt->load(aFontGlSrc->getFont()->getFilePath((StFTFont::Style )aStyleIt),
105
+ aFontGlSrc->getFont()->getFaceIndex((StFTFont::Style )aStyleIt),
106
+ (StFTFont::Style )aStyleIt);
107
}
108
aFontFt->init(aSize, aResolution);
109
aFontNew->changeFont((StFTFont::Subset )anIter) = new StGLFontEntry(aFontFt);
110
111
bool StGLSubtitles::stglInit() {
112
if(!myVertBuf.isValid()) {
113
StArray<StGLVec2> aDummyVert(4);
114
- StArray<StGLVec2> aTexCoords(4);
115
- aTexCoords[0] = StGLVec2(1.0f, 0.0f);
116
- aTexCoords[1] = StGLVec2(1.0f, 1.0f);
117
- aTexCoords[2] = StGLVec2(0.0f, 0.0f);
118
- aTexCoords[3] = StGLVec2(0.0f, 1.0f);
119
120
StGLContext& aCtx = getContext();
121
myVertBuf.init(aCtx, aDummyVert);
122
- myTCrdBuf.init(aCtx, aTexCoords);
123
+ myTCrdBuf.init(aCtx, aDummyVert);
124
125
if(myImgProgram.isNull()) {
126
myImgProgram.create(getRoot()->getContextHandle(), new StImgProgram());
127
128
myShowItems.add(aNewSubItem);
129
}
130
131
- const StGLVCorner aCorner = parseCorner(myPlace->getValue());
132
+ const StGLVCorner aCorner = parseCorner(params.Place->getValue());
133
bool toResize = myCorner.v != aCorner;
134
myCorner.v = aCorner;
135
switch(myCorner.v) {
136
case ST_VCORNER_TOP: {
137
- const int aDisp = myRoot->scale((int )myTopDY->getValue()) + myRoot->getRootMargins().top;
138
+ const int aDisp = myRoot->scale((int )params.TopDY->getValue()) + myRoot->getRootMargins().top;
139
if(getRectPx().top() != aDisp) {
140
toResize = true;
141
changeRectPx().moveTopTo(aDisp);
142
143
break;
144
}
145
case ST_VCORNER_BOTTOM: {
146
- const int aDisp = -myRoot->scale((int )myBottomDY->getValue()) - myRoot->getRootMargins().bottom;
147
+ const int aDisp = -myRoot->scale((int )params.BottomDY->getValue()) - myRoot->getRootMargins().bottom;
148
if(getRectPx().top() != aDisp) {
149
toResize = true;
150
changeRectPx().moveTopTo(aDisp);
151
152
ST_DEBUG_LOG("(" + myPTS + ") myShowItems.myText= '" + myShowItems.myText + "'\n" + aLog);*/
153
}
154
155
- const FontSize aNewSize = (FontSize )(int )myFontSize->getValue();
156
+ const FontSize aNewSize = (FontSize )(int )params.FontSize->getValue();
157
if(!myText.isEmpty()
158
&& aNewSize != mySize) {
159
mySize = aNewSize;
160
161
}
162
163
StGLContext& aCtx = getContext();
164
- if(myFormatter.getParser() != (StGLTextFormatter::Parser )myParser->getValue()) {
165
- myFormatter.setupParser((StGLTextFormatter::Parser )myParser->getValue());
166
+ if(myFormatter.getParser() != (StGLTextFormatter::Parser )params.Parser->getValue()) {
167
+ myFormatter.setupParser((StGLTextFormatter::Parser )params.Parser->getValue());
168
myToRecompute = true;
169
}
170
if(!myText.isEmpty()) {
171
172
173
switch(theView) {
174
case ST_DRAW_LEFT:
175
- myTextDX = -myParallax->getValue() * GLfloat(0.5 * 0.001 * myRoot->getRootRectGl().width());
176
+ myTextDX = -params.Parallax->getValue() * GLfloat(0.5 * 0.001 * myRoot->getRootRectGl().width());
177
break;
178
case ST_DRAW_RIGHT:
179
- myTextDX = myParallax->getValue() * GLfloat(0.5 * 0.001 * myRoot->getRootRectGl().width());
180
+ myTextDX = params.Parallax->getValue() * GLfloat(0.5 * 0.001 * myRoot->getRootRectGl().width());
181
break;
182
case ST_DRAW_MONO:
183
default:
184
185
return;
186
}
187
188
- aCtx.core20fwd->glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
189
- aCtx.core20fwd->glEnable(GL_BLEND);
190
- myTexture.bind(aCtx);
191
+ StHandle<StStereoParams> aParams;
192
+ StFormat aStFormat = StFormat_Mono;
193
+ unsigned int aView = theView;
194
+ float aSampleRatio = 1.0f;
195
+ StVec2<int> aFrameDims(0, 0);
196
+ if(StGLImageRegion* anImgRegion = !params.ToApplyStereo.isNull() && params.ToApplyStereo->getValue()
197
+ ? dynamic_cast<StGLImageRegion*>(myParent)
198
+ : NULL) {
199
+ aParams = anImgRegion->getSource();
200
+ if(!aParams.isNull()) {
201
+ aStFormat = aParams->StereoFormat;
202
+ aSampleRatio = anImgRegion->getSampleRatio();
203
+ aFrameDims = anImgRegion->getFrameSize();
204
+ if(aParams->ToSwapLR) {
205
+ // apply swap flag
206
+ switch(aStFormat) {
207
+ case StFormat_SideBySide_LR: aStFormat = StFormat_SideBySide_RL; break;
208
+ case StFormat_SideBySide_RL: aStFormat = StFormat_SideBySide_LR; break;
209
+ case StFormat_TopBottom_LR: aStFormat = StFormat_TopBottom_RL; break;
210
+ case StFormat_TopBottom_RL: aStFormat = StFormat_TopBottom_LR; break;
211
+ default: break;
212
+ }
213
+ }
214
+ // swap views
215
+ if(aStFormat == StFormat_SideBySide_RL) {
216
+ aStFormat = StFormat_SideBySide_LR;
217
+ if(theView == ST_DRAW_RIGHT) {
218
+ aView = ST_DRAW_LEFT;
219
+ } else if(theView == ST_DRAW_LEFT) {
220
+ aView = ST_DRAW_RIGHT;
221
+ }
222
+ } else if(aStFormat == StFormat_TopBottom_RL) {
223
+ aStFormat = StFormat_TopBottom_LR;
224
+ if(theView == ST_DRAW_RIGHT) {
225
+ aView = ST_DRAW_LEFT;
226
+ } else if(theView == ST_DRAW_LEFT) {
227
+ aView = ST_DRAW_RIGHT;
228
+ }
229
+ }
230
+ // reset
231
+ if(aStFormat != StFormat_SideBySide_LR
232
+ && aStFormat != StFormat_TopBottom_LR) {
233
+ aSampleRatio = 1.0f;
234
+ }
235
+ }
236
+ }
237
238
// update vertices
239
- StRectI_t aRect = getRectPxAbsolute();
240
- aRect.top() = aRect.bottom() - myTexture.getSizeY();
241
- aRect.left() = aRect.left() + aRect.width() / 2 - myTexture.getSizeX() / 2;
242
- aRect.right() = aRect.left() + myTexture.getSizeX();
243
+ StVec2<int> anImgSize (myTexture.getSizeX(), myTexture.getSizeY()), anOffset (0, 0);
244
+ StArray<StGLVec2> aVertices(4), aTexCoords(4);
245
+ aTexCoords[0] = StGLVec2(1.0f, 0.0f);
246
+ aTexCoords[1] = StGLVec2(1.0f, 1.0f);
247
+ aTexCoords[2] = StGLVec2(0.0f, 0.0f);
248
+ aTexCoords[3] = StGLVec2(0.0f, 1.0f);
249
+ if(aSampleRatio >= 1.0f) {
250
+ anImgSize.x() = int(double(anImgSize.x()) * aSampleRatio);
251
+ } else {
252
+ anImgSize.y() = int(double(anImgSize.y()) / aSampleRatio);
253
+ }
254
+ const double aFontScale = double(getRoot()->getScale()) * myShowItems.Scale * params.FontSize->getValue() / params.FontSize->getDefValue();
255
+ anImgSize.x() = int(double(anImgSize.x()) * aFontScale);
256
+ anImgSize.y() = int(double(anImgSize.y()) * aFontScale);
257
+
258
+ switch(aStFormat) {
259
+ case StFormat_SideBySide_LR: {
260
+ anImgSize.x() /= 2;
261
+ const int anOffsetX = int(aFontScale * ((aFrameDims.x() * 2 - myTexture.getSizeX()) / 2));
262
+ if(aView == ST_DRAW_LEFT) {
263
+ aTexCoords[0].x() = aTexCoords[1].x() = 0.5f;
264
+ aTexCoords[2].x() = aTexCoords[3].x() = 0.0f;
265
+ anOffset.x() = anOffsetX;
266
+ } else if(aView == ST_DRAW_RIGHT) {
267
+ aTexCoords[0].x() = aTexCoords[1].x() = 1.0f;
268
+ aTexCoords[2].x() = aTexCoords[3].x() = 0.5f;
269
+ anOffset.x() = -anOffsetX;
270
+ }
271
+ break;
272
+ }
273
+ case StFormat_TopBottom_LR: {
274
+ anImgSize.y() /= 2;
275
+ const int anOffsetY = int(aFontScale * ((aFrameDims.y() * 2 - myTexture.getSizeY()) / 2));
276
+ if(aView == ST_DRAW_LEFT) {
277
+ aTexCoords[0].y() = aTexCoords[2].y() = 0.0f;
278
+ aTexCoords[1].y() = aTexCoords[3].y() = 0.5f;
279
+ anOffset.y() = -anOffsetY;
280
+ } else if(aView == ST_DRAW_RIGHT) {
281
+ aTexCoords[0].y() = aTexCoords[2].y() = 0.5f;
282
+ aTexCoords[1].y() = aTexCoords[3].y() = 1.0f;
283
+ anOffset.y() = anOffsetY;
284
+ }
285
+ break;
286
+ }
287
+ default: {
288
+ break;
289
+ }
290
+ }
291
+ if(aView == ST_DRAW_LEFT) {
292
+ anOffset.x() -= (int )params.Parallax->getValue();
293
+ } else if(aView == ST_DRAW_RIGHT) {
294
+ anOffset.x() += (int )params.Parallax->getValue();
295
+ }
296
297
- StArray<StGLVec2> aVertices(4);
298
+ StRectI_t aRect = getRectPxAbsolute();
299
+ aRect.bottom() += anOffset.y();
300
+ aRect.top() = aRect.bottom() - anImgSize.y();
301
+ aRect.left() = aRect.left() + aRect.width() / 2 - anImgSize.x() / 2 + anOffset.x();
302
+ aRect.right() = aRect.left() + anImgSize.x();
303
myRoot->getRectGl(aRect, aVertices);
304
myVertBuf.init(aCtx, aVertices);
305
+ myTCrdBuf.init(aCtx, aTexCoords);
306
307
+ aCtx.core20fwd->glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
308
+ aCtx.core20fwd->glEnable(GL_BLEND);
309
+ myTexture.bind(aCtx);
310
myImgProgram->use(aCtx);
311
312
myVertBuf.bindVertexAttrib(aCtx, myImgProgram->getVVertexLoc());
313
sview-17_04.tar.gz/StGLWidgets/StGLTable.cpp -> sview-20_08.tar.gz/StGLWidgets/StGLTable.cpp
Changed
75
1
2
/**
3
* StGLWidgets, small C++ toolkit for writing GUI using OpenGL.
4
- * Copyright © 2014-2015 Kirill Gavrilov <kirill@sview.ru>
5
+ * Copyright © 2014-2017 Kirill Gavrilov <kirill@sview.ru>
6
*
7
* Distributed under the Boost Software License, Version 1.0.
8
* See accompanying file license-boost.txt or copy at
9
10
#include <StGLWidgets/StGLCombobox.h>
11
#include <StGLWidgets/StGLCheckbox.h>
12
#include <StGLWidgets/StGLMenuItem.h>
13
+#include <StGLWidgets/StGLRangeFieldFloat32.h>
14
#include <StGLWidgets/StGLRootWidget.h>
15
16
#include <StGL/StGLContext.h>
17
18
19
#include <StStrings/StDictionary.h>
20
#include <StSettings/StEnumParam.h>
21
+#include <StSettings/StFloat32Param.h>
22
23
#include <stAssert.h>
24
25
26
int aCol2Width = 0;
27
StHandle<StBoolParamNamed> aBool;
28
StHandle<StEnumParam> anEnum;
29
+ StHandle<StFloat32Param> aFloat32;
30
const int anIconMargin = myRoot->scale(8);
31
const int anIconWidth = anIconMargin * 2 + myRoot->scale(16);
32
StMarginsI aCheckMargins;
33
34
for(size_t aValIter = 0; aValIter < aValues.size(); ++aValIter) {
35
aCol2Width = stMax(aCol2Width, aButton->computeWidth(aValues[aValIter]));
36
}
37
+ } else if(aFloat32.downcastFrom(aParam)) {
38
+ StGLRangeFieldFloat32* aRange = new StGLRangeFieldFloat32(&anItem, aFloat32,
39
+ 0, 0, StGLCorner(ST_VCORNER_CENTER, ST_HCORNER_RIGHT),
40
+ StGLRangeFieldFloat32::RangeStyle_Seekbar, myRoot->scale(18));
41
+ aRange->changeRectPx().right() = myRoot->scale(50);
42
+ aRange->changeMargins().left = myRoot->scale(8);
43
+ aRange->changeMargins().right = myRoot->scale(8);
44
+ aRange->setCorner(StGLCorner(ST_VCORNER_TOP, ST_HCORNER_LEFT));
45
+ if(!aFloat32->getFormat().isEmpty()) {
46
+ aRange->setFormat(aFloat32->getFormat());
47
+ }
48
+ aCol2Width = stMax(aCol2Width, aRange->getRectPx().width());
49
} else {
50
// skip
51
}
52
53
continue;
54
}
55
56
- StGLCombobox* aButton = dynamic_cast<StGLCombobox* >(anItem.getItem());
57
- if(aButton != NULL) {
58
+ if(StGLCombobox* aButton = dynamic_cast<StGLCombobox* >(anItem.getItem())) {
59
anItem.getItem()->changeRectPx().right() = aWidget->getRectPx().left() + aCol2Width;
60
aButton->setWidth(aCol2Width);
61
+ } else if(dynamic_cast<StGLRangeFieldFloat32* >(anItem.getItem()) != NULL) {
62
+ anItem.getItem()->changeRectPx().right() = aWidget->getRectPx().left() + aCol2Width;
63
}
64
}
65
66
67
aLabelText = aBool->getName();
68
} else if(anEnum.downcastFrom(aParam)) {
69
aLabelText = anEnum->getName();
70
+ } else if(aFloat32.downcastFrom(aParam)) {
71
+ aLabelText = aFloat32->getName();
72
} else {
73
// skip
74
}
75
sview-17_04.tar.gz/StGLWidgets/StGLTextArea.cpp -> sview-20_08.tar.gz/StGLWidgets/StGLTextArea.cpp
Changed
71
1
2
/**
3
* StGLWidgets, small C++ toolkit for writing GUI using OpenGL.
4
- * Copyright © 2009-2017 Kirill Gavrilov <kirill@sview.ru>
5
+ * Copyright © 2009-2020 Kirill Gavrilov <kirill@sview.ru>
6
*
7
* Distributed under the Boost Software License, Version 1.0.
8
* See accompanying file license-boost.txt or copy at
9
10
StRectD_t aTextRectGl = getRoot()->getRectGl(getAbsolute(aTextRectPx));
11
12
// size corrector for FTGL
13
- StRectD_t zparams; getCamera()->getZParams(zparams);
14
- GLfloat aSizeOut = 2.0f * GLfloat(zparams.top()) / GLfloat(getRoot()->getRootFullSizeY());
15
-
16
- StGLMatrix aModelMat;
17
- aModelMat.translate(StGLVec3(getRoot()->getScreenDispX() + myTextDX, 0.0f, -getCamera()->getZScreen()));
18
- aModelMat.translate(StGLVec3(GLfloat(aTextRectGl.left()),
19
- GLfloat(aTextRectGl.top()),
20
- 0.0f));
21
- aModelMat.scale(aSizeOut, aSizeOut, 0.0f);
22
+ StRectD_t aZParams; getCamera()->getZParams(aZParams);
23
+ const GLfloat aSizeOut = 2.0f * GLfloat(aZParams.top()) / GLfloat(getRoot()->getRootFullSizeY());
24
25
aCtx.core20fwd->glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
26
aCtx.core20fwd->glEnable(GL_BLEND);
27
28
29
StGLTextBorderProgram& aBorderProgram = myRoot->getTextBorderProgram();
30
aBorderProgram.use(aCtx);
31
- aBorderProgram.setModelMat(aCtx, aModelMat);
32
+ aBorderProgram.setDisplacement(aCtx,
33
+ StGLVec3(GLfloat(aTextRectGl.left()) + getRoot()->getScreenDispX() + myTextDX,
34
+ GLfloat(aTextRectGl.top()), 0.0f),
35
+ aSizeOut);
36
37
aBorderProgram.setColor(aCtx, myBorderColor);
38
myBorderOVertBuf.bindVertexAttrib(aCtx, aBorderProgram.getVVertexLoc());
39
40
aCtx.core20fwd->glActiveTexture(GL_TEXTURE0); // our shader is bound to first texture unit
41
StGLTextProgram& aTextProgram = myRoot->getTextProgram();
42
aTextProgram.use(aCtx);
43
- aTextProgram.setModelMat(aCtx, aModelMat);
44
+ aTextProgram.setDisplacement(aCtx,
45
+ StGLVec3(GLfloat(aTextRectGl.left()) + getRoot()->getScreenDispX() + myTextDX,
46
+ GLfloat(aTextRectGl.top()), 0.0f),
47
+ aSizeOut);
48
aTextProgram.setColor(aCtx, myToDrawShadow ? myShadowColor : aTextColor);
49
-
50
drawText(aCtx);
51
52
if(myToDrawShadow) {
53
- aModelMat.initIdentity();
54
aTextRectPx.left() -= 1;
55
aTextRectPx.top() -= 1;
56
aTextRectGl = getRoot()->getRectGl(getAbsolute(aTextRectPx));
57
- aModelMat.translate(StGLVec3(getRoot()->getScreenDispX() + myTextDX, 0.0f, -getCamera()->getZScreen()));
58
- aModelMat.translate(StGLVec3(GLfloat(aTextRectGl.left()),
59
- GLfloat(aTextRectGl.top()),
60
- 0.0f));
61
- aModelMat.scale(aSizeOut, aSizeOut, 0.0f);
62
63
- aTextProgram.setModelMat(aCtx, aModelMat);
64
+ aTextProgram.setDisplacement(aCtx,
65
+ StGLVec3(GLfloat(aTextRectGl.left()) + getRoot()->getScreenDispX() + myTextDX,
66
+ GLfloat(aTextRectGl.top()), 0.0f),
67
+ aSizeOut);
68
aTextProgram.setColor(aCtx, aTextColor);
69
70
drawText(aCtx);
71
sview-17_04.tar.gz/StGLWidgets/StGLTextBorderProgram.cpp -> sview-20_08.tar.gz/StGLWidgets/StGLTextBorderProgram.cpp
Changed
48
1
2
/**
3
* StGLWidgets, small C++ toolkit for writing GUI using OpenGL.
4
- * Copyright © 2009-2015 Kirill Gavrilov <kirill@sview.ru>
5
+ * Copyright © 2009-2020 Kirill Gavrilov <kirill@sview.ru>
6
*
7
* Distributed under the Boost Software License, Version 1.0.
8
* See accompanying file license-boost.txt or copy at
9
10
theCtx.core20fwd->glUniformMatrix4fv(myUniformProjMat, 1, GL_FALSE, theProjMat);
11
}
12
13
-void StGLTextBorderProgram::setModelMat(StGLContext& theCtx,
14
- const StGLMatrix& theModelMat) {
15
- theCtx.core20fwd->glUniformMatrix4fv(myUniformModelMat, 1, GL_FALSE, theModelMat);
16
+void StGLTextBorderProgram::setDisplacement(StGLContext& theCtx,
17
+ const StGLVec3& theDisp,
18
+ const float theScale) {
19
+ theCtx.core20fwd->glUniform4fv(myUniformDispl, 1, StGLVec4(theDisp, theScale));
20
}
21
22
void StGLTextBorderProgram::setColor(StGLContext& theCtx,
23
24
bool StGLTextBorderProgram::init(StGLContext& theCtx) {
25
const char VERTEX_SHADER[] =
26
"uniform mat4 uProjMat; \
27
- uniform mat4 uModelMat; \
28
+ uniform vec4 uDisp; \
29
attribute vec4 vVertex; \
30
void main(void) { \
31
- gl_Position = uProjMat * uModelMat * vVertex; \
32
+ gl_Position = uProjMat * (vec4(vVertex.xy * uDisp.w, 0.0, 1.0) + vec4(uDisp.xyz, 0.0)); \
33
}";
34
35
const char FRAGMENT_SHADER[] =
36
37
}
38
39
myUniformProjMat = StGLProgram::getUniformLocation(theCtx, "uProjMat");
40
- myUniformModelMat = StGLProgram::getUniformLocation(theCtx, "uModelMat");
41
+ myUniformDispl = StGLProgram::getUniformLocation(theCtx, "uDisp");
42
myUniformColor = StGLProgram::getUniformLocation(theCtx, "uColor");
43
return myUniformProjMat.isValid()
44
- && myUniformModelMat.isValid()
45
+ && myUniformDispl.isValid()
46
&& myUniformColor.isValid();
47
}
48
sview-17_04.tar.gz/StGLWidgets/StGLTextProgram.cpp -> sview-20_08.tar.gz/StGLWidgets/StGLTextProgram.cpp
Changed
57
1
2
/**
3
* StGLWidgets, small C++ toolkit for writing GUI using OpenGL.
4
- * Copyright © 2009-2015 Kirill Gavrilov <kirill@sview.ru>
5
+ * Copyright © 2009-2020 Kirill Gavrilov <kirill@sview.ru>
6
*
7
* Distributed under the Boost Software License, Version 1.0.
8
* See accompanying file license-boost.txt or copy at
9
10
theCtx.core20fwd->glUniformMatrix4fv(myUniformProjMat, 1, GL_FALSE, theProjMat);
11
}
12
13
-void StGLTextProgram::setModelMat(StGLContext& theCtx,
14
- const StGLMatrix& theModelMat) {
15
- theCtx.core20fwd->glUniformMatrix4fv(myUniformModelMat, 1, GL_FALSE, theModelMat);
16
+void StGLTextProgram::setDisplacement(StGLContext& theCtx,
17
+ const StGLVec3& theDisp,
18
+ const float theScale) {
19
+ theCtx.core20fwd->glUniform4fv(myUniformDispl, 1, StGLVec4(theDisp, theScale));
20
}
21
22
void StGLTextProgram::setColor(StGLContext& theCtx,
23
24
bool StGLTextProgram::init(StGLContext& theCtx) {
25
const char VERTEX_SHADER[] =
26
"uniform mat4 uProjMat; \
27
- uniform mat4 uModelMat; \
28
+ uniform vec4 uDisp; \
29
attribute vec4 vVertex; \
30
attribute vec2 vTexCoord; \
31
varying vec2 fTexCoord; \
32
void main(void) { \
33
fTexCoord = vTexCoord; \
34
- gl_Position = uProjMat * uModelMat * vVertex; \
35
+ gl_Position = uProjMat * (vec4(vVertex.xy * uDisp.w, 0.0, 1.0) + vec4(uDisp.xyz, 0.0)); \
36
}";
37
38
const char FRAGMENT_GET_RED[] =
39
40
}
41
42
myUniformProjMat = StGLProgram::getUniformLocation(theCtx, "uProjMat");
43
- myUniformModelMat = StGLProgram::getUniformLocation(theCtx, "uModelMat");
44
+ myUniformDispl = StGLProgram::getUniformLocation(theCtx, "uDisp");
45
myUniformColor = StGLProgram::getUniformLocation(theCtx, "uTextColor");
46
47
StGLVarLocation aUniformTexture = StGLProgram::getUniformLocation(theCtx, "uTexture");
48
49
}
50
51
return myUniformProjMat.isValid()
52
- && myUniformModelMat.isValid()
53
+ && myUniformDispl.isValid()
54
&& myUniformColor.isValid()
55
&& aUniformTexture.isValid();
56
}
57
sview-17_04.tar.gz/StGLWidgets/StGLTextureButton.cpp -> sview-20_08.tar.gz/StGLWidgets/StGLTextureButton.cpp
Changed
72
1
2
* Initialize all programs.
3
*/
4
bool init(StGLContext& theCtx) {
5
- /**const char FRAGMENT_GET_RED[] =
6
+ const char* FRAGMENT_GET_ALPHA = theCtx.arbTexRG
7
+ ? "#define stTextureAlpha(theSampler, theCoords) texture2D(theSampler, theCoords).r\n"
8
+ : "#define stTextureAlpha(theSampler, theCoords) texture2D(theSampler, theCoords).a\n";
9
+ const char FRAGMENT_GET_COLOR[] =
10
"uniform sampler2D uTexture;\n"
11
"uniform vec4 uColor;\n"
12
"vec4 getColor(in vec2 theTexCoord) {\n"
13
" vec4 aColor = uColor;\n"
14
- " aColor.a *= 1.0 - texture2D(uTexture, theTexCoord).r;\n"
15
- " return aColor;\n"
16
- "}\n\n";*/
17
-
18
- const char FRAGMENT_GET_ALPHA[] =
19
- "uniform sampler2D uTexture;\n"
20
- "uniform vec4 uColor;\n"
21
- "vec4 getColor(in vec2 theTexCoord) {\n"
22
- " vec4 aColor = uColor;\n"
23
- " aColor.a *= 1.0 - texture2D(uTexture, theTexCoord).a;\n"
24
+ " aColor.a *= 1.0 - stTextureAlpha(uTexture, theTexCoord);\n"
25
" return aColor;\n"
26
"}\n\n";
27
+
28
registerFragmentShaderPart(FragSection_GetColor, FragGetColor_Alpha,
29
- ///theCtx.arbTexRG ? FRAGMENT_GET_RED :
30
- FRAGMENT_GET_ALPHA);
31
+ StString(FRAGMENT_GET_ALPHA) + FRAGMENT_GET_COLOR);
32
33
setFragmentShaderPart(theCtx, FragSection_GetColor, FragGetColor_RGB);
34
if(!initProgram(theCtx)) {
35
36
37
void StGLTextureButton::setTexturePath(const StString* theTexturesPaths,
38
const size_t theCount) {
39
+ if(myTextures.isNull()) {
40
+ if(theCount != 0) {
41
+ myTextures = new StGLTextureArray(theCount);
42
+ } else {
43
+ #ifdef ST_DEBUG
44
+ ST_DEBUG_LOG_AT("WARNING, Attempt to set an empty list of textures to StGLTextureButton!");
45
+ #endif
46
+ return;
47
+ }
48
+ }
49
const size_t aNbTextures = (theCount > myTextures->size()) ? myTextures->size() : theCount;
50
#ifdef ST_DEBUG
51
if(theCount != myTextures->size()) {
52
53
}
54
55
bool StGLTextureButton::stglInit() {
56
+ if(myTextures.isNull()) {
57
+ return false;
58
+ }
59
+
60
StGLContext& aCtx = getContext();
61
const StHandle<StResourceManager>& aResMgr = getRoot()->getResourceManager();
62
for(size_t aFaceIter = 0; aFaceIter < myTextures->size(); ++aFaceIter) {
63
64
}
65
66
GLint anInternalFormat = GL_RGB;
67
- if(!StGLTexture::getInternalFormat(aCtx, anImage.getPlane(), anInternalFormat)) {
68
+ if(!StGLTexture::getInternalFormat(aCtx, anImage.getPlane().getFormat(), anInternalFormat)) {
69
ST_ERROR_LOG("StGLTextureButton, texture '" + aTexture.getName() + "' has unsupported format!");
70
continue;
71
}
72
sview-17_04.tar.gz/StGLWidgets/StGLWidget.cpp -> sview-20_08.tar.gz/StGLWidgets/StGLWidget.cpp
Changed
16
1
2
return computeAbsolutePos(myParent->getRectPxAbsolute(), theRectPx, myCorner);
3
}
4
5
-void StGLWidget::stglScissorRect(StGLBoxPx& theScissorRect) const {
6
- myRoot->stglScissorRect(getRectPxAbsolute(), theScissorRect);
7
+void StGLWidget::stglScissorRect2d(StGLBoxPx& theScissorRect) const {
8
+ myRoot->stglScissorRect2d(getRectPxAbsolute(), theScissorRect);
9
+}
10
+
11
+void StGLWidget::stglScissorRect3d(StGLBoxPx& theScissorRect) const {
12
+ myRoot->stglScissorRect3d(getRectPxAbsolute(), theScissorRect);
13
}
14
15
StPointD_t StGLWidget::getPointGl(const StPointD_t& thePointZo) const {
16
sview-17_04.tar.gz/StGLWidgets/StGLWidgets.rc -> sview-20_08.tar.gz/StGLWidgets/StGLWidgets.rc
Changed
10
1
2
BEGIN
3
VALUE "FileDescription", "OpenGL Widgets library\000"
4
VALUE "FileVersion", SVIEW_SDK_VER_STRING "\000"
5
- VALUE "LegalCopyright", "\251 2009-2017 Kirill Gavrilov\000"
6
+ VALUE "LegalCopyright", "\251 2009-2020 Kirill Gavrilov\000"
7
VALUE "ProductName", "StGLWidgets\000"
8
VALUE "ProductVersion", SVIEW_SDK_VER_STRING "\000"
9
VALUE "OfficialSite", "www.sview.ru\000"
10
sview-17_04.tar.gz/StImageViewer/StImageLoader.cpp -> sview-20_08.tar.gz/StImageViewer/StImageLoader.cpp
Changed
387
1
2
/**
3
- * Copyright © 2007-2017 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2007-2019 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* StImageViewer program is free software: you can redistribute it and/or modify
7
* it under the terms of the GNU General Public License as published by
8
9
#include "StImageViewerStrings.h"
10
#include "StImageViewerGUI.h"
11
12
+#include "../StMoviePlayer/StMoviePlayerInfo.h"
13
+
14
#include <StAV/StAVImage.h>
15
#include <StThreads/StThread.h>
16
17
using namespace StImageViewerStrings;
18
19
const char* StImageLoader::ST_IMAGES_MIME_STRING = ST_IMAGE_PLUGIN_MIME_CHAR;
20
+const char* StImageLoader::ST_VIDEOS_MIME_STRING = ST_VIDEO_PLUGIN_MIME_CHAR;
21
22
namespace {
23
24
25
const StHandle<StGLTextureQueue>& theTextureQueue,
26
const GLint theMaxTexDim)
27
: myMimeList(ST_IMAGES_MIME_STRING),
28
+ myVideoMimeList(ST_VIDEOS_MIME_STRING),
29
myResMgr(theResMgr),
30
myLangMap(theLangMap),
31
myPlayList(thePlayList),
32
33
myMsgQueue(theMsgQueue),
34
myImageLib(theImageLib),
35
myAction(Action_NONE),
36
+ myIsTheaterMode(false),
37
myToStickPano360(false),
38
myToFlipCubeZ6x1(false),
39
- myToFlipCubeZ3x2(false) {
40
+ myToFlipCubeZ3x2(false),
41
+ myToSwapJps(false) {
42
myPlayList->setExtensions(myMimeList.getExtensionsList());
43
myThread = new StThread(threadFunction, (void* )this, "StImageLoader");
44
}
45
46
}
47
48
inline StHandle<StImage> scaledImage(StHandle<StImageFile>& theRef,
49
+ const StGLDeviceCaps& theCaps,
50
const size_t theMaxSizeX,
51
const size_t theMaxSizeY,
52
StCubemap theCubemap,
53
54
return theRef;
55
}
56
57
- if(theCubemap == StCubemap_Packed) {
58
+ const bool toConvertRgb = !theCaps.isSupportedFormat(theRef->getPlane().getFormat());
59
+ StImagePlane::ImgFormat anRgbImgFormat = StImagePlane::ImgRGB;
60
+ if(toConvertRgb) {
61
+ switch(theRef->getColorModel()) {
62
+ case StImage::ImgColor_RGB:
63
+ anRgbImgFormat = StImagePlane::ImgRGB;
64
+ break;
65
+ case StImage::ImgColor_RGBA:
66
+ anRgbImgFormat = StImagePlane::ImgRGBA;
67
+ break;
68
+ case StImage::ImgColor_GRAY:
69
+ anRgbImgFormat = StImagePlane::ImgGray;
70
+ break;
71
+ default:
72
+ anRgbImgFormat = StImagePlane::ImgRGB;
73
+ break;
74
+ }
75
+ }
76
+
77
+ if(theCubemap == StCubemap_Packed) { // skip scaling for StCubemap_PackedEAC
78
size_t aSizesY[4] = {};
79
bool toResize = false;
80
size_t aMulX = (thePairRatio == StPairRatio_HalfWidth) ? 2 : 1;
81
82
toResize = true;
83
}
84
}
85
- if(!toResize) {
86
+ if(!toResize && !toConvertRgb) {
87
return theRef;
88
}
89
90
StHandle<StImage> anImage = new StImage();
91
- anImage->setColorModel(theRef->getColorModel());
92
- anImage->setColorScale(theRef->getColorScale());
93
+ if(toConvertRgb) {
94
+ anImage->setColorModelPacked(anRgbImgFormat);
95
+ anImage->setColorScale(StImage::ImgScale_Full);
96
+ } else {
97
+ anImage->setColorModel(theRef->getColorModel());
98
+ anImage->setColorScale(theRef->getColorScale());
99
+ }
100
101
double aRatioX = double(aSizesY[0] * theCubeCoeffs[0] * aMulX) / double(theRef->getSizeX());
102
double aRatioY = double(aSizesY[0] * theCubeCoeffs[1] * aMulY) / double(theRef->getSizeY());
103
anImage->setPixelRatio(float(double(theRef->getPixelRatio()) * aRatioY / aRatioX));
104
for(size_t aPlaneId = 0; aPlaneId < 4; ++aPlaneId) {
105
+ if(toConvertRgb) {
106
+ if(aPlaneId != 0) {
107
+ continue;
108
+ }
109
+ if(!anImage->changePlane(0).initTrash(anRgbImgFormat,
110
+ aSizesY[0] * theCubeCoeffs[0] * aMulX,
111
+ aSizesY[0] * theCubeCoeffs[1] * aMulY)) {
112
+ ST_ERROR_LOG("Scale failed!");
113
+ return theRef;
114
+ }
115
+ continue;
116
+ }
117
+
118
const StImagePlane& aFromPlane = theRef->getPlane(aPlaneId);
119
if(aFromPlane.isNull()) {
120
continue;
121
}
122
123
+ size_t aPlanesSizeX = aSizesY[aPlaneId] * theCubeCoeffs[0] * aMulX;
124
+ size_t aSizeRowBytes = aPlanesSizeX * aFromPlane.getSizePixelBytes();
125
+ aSizeRowBytes = aSizeRowBytes + (32 - aSizeRowBytes % 32);
126
if(!anImage->changePlane(aPlaneId).initTrash(aFromPlane.getFormat(),
127
aSizesY[aPlaneId] * theCubeCoeffs[0] * aMulX,
128
- aSizesY[aPlaneId] * theCubeCoeffs[1] * aMulY)) {
129
+ aSizesY[aPlaneId] * theCubeCoeffs[1] * aMulY,
130
+ aSizeRowBytes)) {
131
ST_ERROR_LOG("Scale failed!");
132
return theRef;
133
}
134
135
}
136
137
if(theRef->getSizeX() <= theMaxSizeX
138
- && theRef->getSizeY() <= theMaxSizeY) {
139
+ && theRef->getSizeY() <= theMaxSizeY
140
+ && !toConvertRgb) {
141
return theRef;
142
}
143
144
StHandle<StImage> anImage = new StImage();
145
const size_t aSizeX = stMin(theRef->getSizeX(), theMaxSizeX);
146
const size_t aSizeY = stMin(theRef->getSizeY(), theMaxSizeY);
147
- if(!anImage->initTrashLimited(*theRef, aSizeX, aSizeY)
148
- || !StAVImage::resize(*theRef, *anImage)) {
149
- ST_ERROR_LOG("Scale failed!");
150
- return theRef;
151
+ if(toConvertRgb) {
152
+ anImage->setColorModelPacked(anRgbImgFormat);
153
+ anImage->setColorScale(StImage::ImgScale_Full);
154
+ if(!anImage->changePlane().initTrash(anRgbImgFormat, aSizeX, aSizeY)
155
+ || !StAVImage::resize(*theRef, *anImage)) {
156
+ ST_ERROR_LOG("Scale failed!");
157
+ return theRef;
158
+ }
159
+ } else {
160
+ if(!anImage->initTrashLimited(*theRef, aSizeX, aSizeY)
161
+ || !StAVImage::resize(*theRef, *anImage)) {
162
+ ST_ERROR_LOG("Scale failed!");
163
+ return theRef;
164
+ }
165
}
166
theRef->close();
167
return anImage;
168
169
170
StTimer aLoadTimer(true);
171
StFormat aSrcFormatCurr = myStFormatByUser;
172
+ StPanorama aSrcPanorama = StPanorama_OFF;
173
if(anImgType == StImageFile::ST_TYPE_MPO
174
|| anImgType == StImageFile::ST_TYPE_JPEG
175
|| anImgType == StImageFile::ST_TYPE_JPS) {
176
177
StDictEntry& anEntry = anImgInfo->Info.addChange("Jpeg.JpsComment");
178
anEntry.changeValue() = aParser.getJpsComment();
179
}
180
+ if(!aParser.getXMP().isEmpty()) {
181
+ StDictEntry& anEntry = anImgInfo->Info.addChange("Jpeg.XMP");
182
+ anEntry.changeValue() = aParser.getXMP();
183
+ }
184
if(!anImg1.isNull()) {
185
for(size_t anExifId = 0; anExifId < anImg1->Exif.size(); ++anExifId) {
186
metadataFromExif(anImg1->Exif[anExifId], anImgInfo);
187
188
&& aParser.getSrcFormat() != StFormat_AUTO) {
189
aSrcFormatCurr = aParser.getSrcFormat();
190
}
191
+ aSrcPanorama = aParser.getPanorama();
192
193
//aParser.fillDictionary(anImgInfo->Info, true);
194
if(!isParsed) {
195
196
return false;
197
}
198
aRawFileL.freeBuffer();
199
+ aSrcPanorama = anImageFileL->getPanoramaFormat();
200
201
StRawFile aRawFileR;
202
if(StFileNode::isContentProtocolPath(aFilePathRight)) {
203
204
return false;
205
}
206
207
+ aSrcPanorama = anImageFileL->getPanoramaFormat();
208
anImgInfo->StInfoStream = anImageFileL->getFormat();
209
if(myStFormatByUser == StFormat_AUTO) {
210
aSrcFormatCurr = anImgInfo->StInfoStream;
211
212
213
// detect information from file name
214
bool isAnamorphByName = false;
215
- anImgInfo->StInfoFileName = st::formatFromName(aTitleString, isAnamorphByName);
216
+ anImgInfo->StInfoFileName = st::formatFromName(aTitleString, myToSwapJps, isAnamorphByName);
217
if(aSrcFormatCurr == StFormat_AUTO
218
&& anImgInfo->StInfoFileName != StFormat_AUTO) {
219
aSrcFormatCurr = anImgInfo->StInfoFileName;
220
221
aSrcFormatCurr = StFormat_SeparateFrames;
222
}
223
224
+ if(aSrcPanorama != StPanorama_OFF) {
225
+ theParams->ViewingMode = StStereoParams::getViewSurfaceForPanoramaSource(aSrcPanorama, true);
226
+ }
227
+ if(myIsTheaterMode && theParams->ViewingMode == StViewSurface_Plain) {
228
+ theParams->ViewingMode = StViewSurface_Theater;
229
+ } else if(!myIsTheaterMode && theParams->ViewingMode == StViewSurface_Theater) {
230
+ theParams->ViewingMode = StViewSurface_Plain;
231
+ }
232
+
233
if(myToStickPano360
234
&& theParams->ViewingMode == StViewSurface_Plain) {
235
StPanorama aPano = st::probePanorama(aSrcFormatCurr,
236
theParams->Src1SizeX, theParams->Src1SizeY,
237
theParams->Src2SizeX, theParams->Src2SizeY);
238
- theParams->ViewingMode = (aPano == StPanorama_Cubemap6_1 || aPano == StPanorama_Cubemap3_2)
239
- ? StViewSurface_Cubemap
240
- : StViewSurface_Sphere;
241
+ theParams->ViewingMode = StStereoParams::getViewSurfaceForPanoramaSource(aPano, true);
242
+ }
243
+ StCubemap aSrcCubemap = StCubemap_OFF;
244
+ if(theParams->ViewingMode == StViewSurface_Cubemap) {
245
+ aSrcCubemap = StCubemap_Packed;
246
+ } else if(theParams->ViewingMode == StViewSurface_CubemapEAC) {
247
+ aSrcCubemap = StCubemap_PackedEAC;
248
}
249
- StCubemap aSrcCubemap = theParams->ViewingMode == StViewSurface_Cubemap ? StCubemap_Packed : StCubemap_OFF;
250
251
size_t aCubeCoeffs[2] = {0, 0};
252
- if(aSrcCubemap == StCubemap_Packed) {
253
+ if(aSrcCubemap == StCubemap_Packed
254
+ || aSrcCubemap == StCubemap_PackedEAC) {
255
if(aSizeX1 / 6 == aSizeY1) {
256
aCubeCoeffs[0] = 6;
257
aCubeCoeffs[1] = 1;
258
theParams->ToFlipCubeZ = myToFlipCubeZ6x1;
259
+ } else if(aSizeY1 / 6 == aSizeX1) {
260
+ aCubeCoeffs[0] = 1;
261
+ aCubeCoeffs[1] = 6;
262
+ theParams->ToFlipCubeZ = myToFlipCubeZ6x1;
263
} else if(aSizeX1 / 3 == aSizeY1 / 2) {
264
aCubeCoeffs[0] = 3;
265
aCubeCoeffs[1] = 2;
266
theParams->ToFlipCubeZ = myToFlipCubeZ3x2;
267
+ } else if(aSizeX1 / 2 == aSizeY1 / 3) {
268
+ aCubeCoeffs[0] = 2;
269
+ aCubeCoeffs[1] = 3;
270
+ theParams->ToFlipCubeZ = myToFlipCubeZ3x2;
271
+ } else if(aSrcCubemap == StCubemap_PackedEAC) {
272
+ // EAC on ytb is so cruel, that they don't use squared cube sides!
273
+ if(aSizeX1 > aSizeY1) {
274
+ aCubeCoeffs[0] = 3;
275
+ aCubeCoeffs[1] = 2;
276
+ theParams->ToFlipCubeZ = myToFlipCubeZ3x2;
277
+ } else {
278
+ aCubeCoeffs[0] = 2;
279
+ aCubeCoeffs[1] = 3;
280
+ theParams->ToFlipCubeZ = myToFlipCubeZ3x2;
281
+ }
282
}
283
if(!anImageFileR->isNull()
284
&& (aSizeX1 != aSizeX2 || aSizeY1 != aSizeY2)) {
285
286
}
287
}
288
289
- StHandle<StImage> anImageL = scaledImage(anImageFileL, aSizeXLim, aSizeYLim, aSrcCubemap, aCubeCoeffs, aPairRatio);
290
- StHandle<StImage> anImageR = scaledImage(anImageFileR, aSizeXLim, aSizeYLim, aSrcCubemap, aCubeCoeffs, aPairRatio);
291
+ StHandle<StImage> anImageL = scaledImage(anImageFileL, myTextureQueue->getDeviceCaps(), aSizeXLim, aSizeYLim,
292
+ aSrcCubemap, aCubeCoeffs, aPairRatio);
293
+ StHandle<StImage> anImageR = scaledImage(anImageFileR, myTextureQueue->getDeviceCaps(), aSizeXLim, aSizeYLim,
294
+ aSrcCubemap, aCubeCoeffs, aPairRatio);
295
#ifdef ST_DEBUG
296
const double aScaleTimeMSec = aLoadTimer.getElapsedTimeInMilliSec() - aLoadTimeMSec;
297
if(anImageL != anImageFileL) {
298
299
anImgInfo->Info.add(StArgument(tr(INFO_PIXEL_RATIO),
300
StString(anImageFileL->getPixelRatio())));
301
}
302
- const StString aModelL = anImageFileL->formatImgColorModel();
303
+ const StString aFormatL = anImageFileL->formatImgPixelFormat();
304
if(!anImageFileR->isNull()) {
305
anImgInfo->Info.add(StArgument(tr(INFO_DIMENSIONS),
306
formatSize(anImageL->getSizeX(), anImageL->getSizeY(),
307
theParams->Src1SizeX, theParams->Src1SizeY) + " " + tr(INFO_LEFT) + "\n"
308
+ formatSize(anImageR->getSizeX(), anImageR->getSizeY(),
309
theParams->Src2SizeX, theParams->Src2SizeY) + " " + tr(INFO_RIGHT)));
310
- const StString aModelR = anImageFileR->formatImgColorModel();
311
- if(aModelL == aModelR) {
312
- anImgInfo->Info.add(StArgument(tr(INFO_COLOR_MODEL), aModelL));
313
+ const StString aFormatR = anImageFileR->formatImgPixelFormat();
314
+ if(aFormatL == aFormatR) {
315
+ anImgInfo->Info.add(StArgument(tr(INFO_PIXEL_FORMAT), aFormatL));
316
} else {
317
- anImgInfo->Info.add(StArgument(tr(INFO_COLOR_MODEL),
318
- aModelL + " " + tr(INFO_LEFT) + "\n"
319
- + aModelR + " " + tr(INFO_RIGHT)));
320
+ anImgInfo->Info.add(StArgument(tr(INFO_PIXEL_FORMAT),
321
+ aFormatL + " " + tr(INFO_LEFT) + "\n"
322
+ + aFormatR + " " + tr(INFO_RIGHT)));
323
}
324
} else {
325
anImgInfo->Info.add(StArgument(tr(INFO_DIMENSIONS),
326
formatSize(anImageL->getSizeX(), anImageL->getSizeY(),
327
theParams->Src1SizeX, theParams->Src1SizeY)));
328
- anImgInfo->Info.add(StArgument(tr(INFO_COLOR_MODEL),
329
- aModelL));
330
+ anImgInfo->Info.add(StArgument(tr(INFO_PIXEL_FORMAT),
331
+ aFormatL));
332
}
333
anImgInfo->Info.add(StArgument(tr(INFO_LOAD_TIME), StString(aLoadTimeMSec) + " " + tr(INFO_TIME_MSEC)));
334
myLock.lock();
335
336
aDataResult->initWrapper(aDataLeft);
337
}
338
339
- const StString& aTitle = myLangMap->getValue(StImageViewerStrings::DIALOG_SAVE_SNAPSHOT);
340
- StMIMEList aFilter;
341
+ StOpenFileName anOpenInfo;
342
+ anOpenInfo.Title = myLangMap->getValue(StImageViewerStrings::DIALOG_SAVE_SNAPSHOT);
343
StString aSaveExt;
344
if(toSaveStereo) {
345
switch(theImgType) {
346
case StImageFile::ST_TYPE_PNG:
347
aSaveExt = ST_PNS_EXT;
348
- aFilter.add(StMIME(ST_PNS_MIME, aSaveExt, ST_PNS_DESC));
349
+ anOpenInfo.Filter.add(StMIME(ST_PNS_MIME, aSaveExt, ST_PNS_DESC));
350
break;
351
case StImageFile::ST_TYPE_JPEG:
352
aSaveExt = ST_JPS_EXT;
353
- aFilter.add(StMIME(ST_JPS_MIME, aSaveExt, ST_JPS_DESC));
354
+ anOpenInfo.Filter.add(StMIME(ST_JPS_MIME, aSaveExt, ST_JPS_DESC));
355
break;
356
default:
357
return false;
358
359
switch(theImgType) {
360
case StImageFile::ST_TYPE_PNG:
361
aSaveExt = ST_PNG_EXT;
362
- aFilter.add(StMIME(ST_PNG_MIME, aSaveExt, ST_PNG_DESC));
363
+ anOpenInfo.Filter.add(StMIME(ST_PNG_MIME, aSaveExt, ST_PNG_DESC));
364
break;
365
case StImageFile::ST_TYPE_JPEG:
366
aSaveExt = ST_JPG_EXT;
367
- aFilter.add(StMIME(ST_JPG_MIME, aSaveExt, ST_JPEG_DESC));
368
+ anOpenInfo.Filter.add(StMIME(ST_JPG_MIME, aSaveExt, ST_JPEG_DESC));
369
break;
370
default:
371
return false;
372
}
373
}
374
375
- StString aFileNameSrc, aFolderSrc, aNameSrc, anExtSrc;
376
- StFileNode::getFolderAndFile(theSource->getPath(), aFolderSrc, aFileNameSrc);
377
+ StString aFileNameSrc, aNameSrc, anExtSrc;
378
+ StFileNode::getFolderAndFile(theSource->getPath(), anOpenInfo.Folder, aFileNameSrc);
379
StFileNode::getNameAndExtension(aFileNameSrc, aNameSrc, anExtSrc);
380
- StString aFileToSave = (!aFolderSrc.isEmpty() ? aFolderSrc : "") + ST_FILE_SPLITTER + aNameSrc;
381
- if(StFileNode::openFileDialog(aFolderSrc, aTitle, aFilter, aFileToSave, true)) {
382
+ StString aFileToSave = (!anOpenInfo.Folder.isEmpty() ? anOpenInfo.Folder : "") + ST_FILE_SPLITTER + aNameSrc;
383
+ if(StFileNode::openFileDialog(aFileToSave, anOpenInfo, true)) {
384
if(StFileNode::getExtension(aFileToSave) != aSaveExt) {
385
aFileToSave += StString('.') + aSaveExt;
386
}
387
sview-17_04.tar.gz/StImageViewer/StImageLoader.h -> sview-20_08.tar.gz/StImageViewer/StImageLoader.h
Changed
71
1
2
/**
3
- * Copyright © 2007-2017 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2007-2019 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* StImageViewer program is free software: you can redistribute it and/or modify
7
* it under the terms of the GNU General Public License as published by
8
9
public:
10
11
static const char* ST_IMAGES_MIME_STRING;
12
+ static const char* ST_VIDEOS_MIME_STRING;
13
14
public:
15
16
- ST_LOCAL const StMIMEList& getMimeList() const {
17
- return myMimeList;
18
- }
19
+ ST_LOCAL const StMIMEList& getMimeListImages() const { return myMimeList; }
20
+
21
+ ST_LOCAL const StMIMEList& getMimeListVideo() const { return myVideoMimeList; }
22
23
ST_LOCAL StImageLoader(const StImageFile::ImageClass theImageLib,
24
const StHandle<StResourceManager>& theResMgr,
25
26
ST_LOCAL void setCompressMemory(const bool theToCompress);
27
28
/**
29
+ * Set theater mode.
30
+ */
31
+ ST_LOCAL void setTheaterMode(bool theIsTheater) {
32
+ myIsTheaterMode = theIsTheater;
33
+ }
34
+
35
+ /**
36
* Stick to panorama 360 mode.
37
*/
38
ST_LOCAL void setStickPano360(bool theToStick) {
39
40
myToFlipCubeZ3x2 = theToFlip;
41
}
42
43
+ /**
44
+ * Set if JPS file should be read as Left/Right (TRUE) of as Right/Left (FALSE).
45
+ */
46
+ ST_LOCAL void setSwapJPS(bool theToSwap) { myToSwapJps = theToSwap; }
47
+
48
public: //! @name Signals
49
50
struct {
51
52
private:
53
54
const StMIMEList myMimeList;
55
+ const StMIMEList myVideoMimeList;
56
StHandle<StThread> myThread; //!< main loop thread
57
StHandle<StResourceManager> myResMgr; //!< resource manager
58
StHandle<StLangMap> myLangMap; //!< translations dictionary
59
60
61
volatile StImageFile::ImageClass myImageLib;
62
volatile Action myAction;
63
+ volatile bool myIsTheaterMode; //!< flag indicating theater mode
64
volatile bool myToStickPano360; //!< stick to panorama 360 mode
65
volatile bool myToFlipCubeZ6x1; //!< flip Z within 6x1 cubemap input
66
volatile bool myToFlipCubeZ3x2; //!< flip Z within 3x2 cubemap input
67
+ volatile bool myToSwapJps; //!< read JPS as Left/Right instead of Right/Left
68
69
private: //! @name no copies, please
70
71
sview-17_04.tar.gz/StImageViewer/StImageOpenDialog.cpp -> sview-20_08.tar.gz/StImageViewer/StImageOpenDialog.cpp
Changed
33
1
2
void StImageOpenDialog::dialogLoop() {
3
myPathLeft .clear();
4
myPathRight.clear();
5
- StString aTitle = myPlugin->tr(myState == StImageOpenDialog::Dialog_ActiveDouble
6
+ StOpenFileName anOpenInfo;
7
+ anOpenInfo.Title = myPlugin->tr(myState == StImageOpenDialog::Dialog_ActiveDouble
8
? StImageViewerStrings::DIALOG_OPEN_LEFT
9
: StImageViewerStrings::DIALOG_OPEN_FILE);
10
-
11
- StString aDummy;
12
- if(!StFileNode::openFileDialog(myFolder, aTitle, myPlugin->myLoader->getMimeList(), myPathLeft, false)) {
13
+ anOpenInfo.Folder = myFolder;
14
+ anOpenInfo.Filter = myPlugin->myLoader->getMimeListImages();
15
+ anOpenInfo.FilterTitle = "Image Files";
16
+ anOpenInfo.ExtraFilter = myPlugin->myLoader->getMimeListVideo();
17
+ anOpenInfo.ExtraFilterTitle = "Video Files";
18
+ if(!StFileNode::openFileDialog(myPathLeft, anOpenInfo, false)) {
19
StMutexAuto aLock(myMutex);
20
myState = StImageOpenDialog::Dialog_Inactive;
21
return;
22
} else if(myState == StImageOpenDialog::Dialog_ActiveDouble) {
23
- aTitle = myPlugin->tr(StImageViewerStrings::DIALOG_OPEN_RIGHT);
24
+ anOpenInfo.Title = myPlugin->tr(StImageViewerStrings::DIALOG_OPEN_RIGHT);
25
+ StString aDummy;
26
StFileNode::getFolderAndFile(myPathLeft, myFolder, aDummy);
27
- if(!StFileNode::openFileDialog(myFolder, aTitle, myPlugin->myLoader->getMimeList(), myPathRight, false)) {
28
+ anOpenInfo.Folder = myFolder;
29
+ if(!StFileNode::openFileDialog(myPathRight, anOpenInfo, false)) {
30
StMutexAuto aLock(myMutex);
31
myState = StImageOpenDialog::Dialog_Inactive;
32
return;
33
sview-17_04.tar.gz/StImageViewer/StImagePluginInfo.h -> sview-20_08.tar.gz/StImageViewer/StImagePluginInfo.h
Changed
23
1
2
#define ST_J2K_DESC "J2K - JPEG 2000 image, lossy"
3
4
/**
5
+ *.insp - Insta360 Image (jpeg unstitched panorama)
6
+ */
7
+#define ST_INSP_MIME "image/x-insp"
8
+#define ST_INSP_EXT "insp"
9
+#define ST_INSP_DESC "INSP - Insta360 Image (JPEG)"
10
+
11
+/**
12
*.png - Portable Network Graphics image file, lossless
13
*/
14
#define ST_PNG_MIME "image/x-png"
15
16
ST_JPG_MIME ":" ST_JPG_EXT ":" ST_JPEG_DESC ";" \
17
ST_JPE_MIME ":" ST_JPE_EXT ":" ST_JPEG_DESC ";" \
18
ST_JPEG_MIME ":" ST_JPEG_EXT ":" ST_JPEG_DESC ";" \
19
+ST_INSP_MIME ":" ST_INSP_EXT ":" ST_INSP_DESC ";" \
20
ST_JP2_MIME ":" ST_JP2_EXT ":" ST_JP2_DESC ";" \
21
ST_J2K_MIME ":" ST_J2K_EXT ":" ST_J2K_DESC ";" \
22
ST_PNG_MIME ":" ST_PNG_EXT ":" ST_PNG_DESC ";" \
23
sview-17_04.tar.gz/StImageViewer/StImageViewer.cpp -> sview-20_08.tar.gz/StImageViewer/StImageViewer.cpp
Changed
417
1
2
/**
3
- * Copyright © 2007-2017 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2007-2020 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* StImageViewer program is free software: you can redistribute it and/or modify
7
* it under the terms of the GNU General Public License as published by
8
9
10
namespace {
11
12
- static const char ST_SETTING_SLIDESHOW_DELAY[] = "slideShowDelay";
13
static const char ST_SETTING_LAST_FOLDER[] = "lastFolder";
14
static const char ST_SETTING_RECENT_L[] = "recentL";
15
static const char ST_SETTING_RECENT_R[] = "recentR";
16
17
params.SrcStereoFormat->setName(tr(MENU_MEDIA_SRC_FORMAT));
18
params.ToShowPlayList->setName(tr(PLAYLIST));
19
params.ToShowAdjustImage->setName(tr(MENU_VIEW_IMAGE_ADJUST));
20
+ params.ToSwapJPS->setName(tr(OPTION_SWAP_JPS));
21
params.ToStickPanorama->setName(tr(MENU_VIEW_STICK_PANORAMA360));
22
params.ToFlipCubeZ6x1->setName(tr(MENU_VIEW_FLIPZ_CUBE6x1));
23
params.ToFlipCubeZ3x2->setName(tr(MENU_VIEW_FLIPZ_CUBE3x2));
24
25
params.ToShowFps->setName(tr(MENU_SHOW_FPS));
26
params.ToShowMenu->setName(stCString("Show main menu"));
27
params.ToShowTopbar->setName(stCString("Show top toolbar"));
28
+ params.ToShowBottom->setName(stCString("Show bottom toolbar"));
29
+ params.SlideShowDelay->setName(stCString("Slideshow delay"));
30
params.IsMobileUI->setName(stCString("Mobile UI"));
31
params.ToHideStatusBar->setName("Hide system status bar");
32
params.ToHideNavBar ->setName(tr(OPTION_HIDE_NAVIGATION_BAR));
33
+ params.IsExclusiveFullScreen->setName(tr(MENU_EXCLUSIVE_FULLSCREEN));
34
params.IsVSyncOn->setName(tr(MENU_VSYNC));
35
params.ToOpenLast->setName(tr(OPTION_OPEN_LAST_ON_STARTUP));
36
params.ToSaveRecent->setName(stCString("Remember recent file"));
37
38
myEventLoaded(false),
39
//
40
mySlideShowTimer(false),
41
- mySlideShowDelay(4.0),
42
//
43
myToCheckUpdates(true),
44
myToSaveSrcFormat(false),
45
46
params.ToShowPlayList->signals.onChanged = stSlot(this, &StImageViewer::doShowPlayList);
47
params.ToShowAdjustImage = new StBoolParamNamed(false, stCString("showAdjustImage"));
48
params.ToShowAdjustImage->signals.onChanged = stSlot(this, &StImageViewer::doShowAdjustImage);
49
+ params.ToSwapJPS = new StBoolParamNamed(false, stCString("toSwapJPS"));
50
+ params.ToSwapJPS->signals.onChanged = stSlot(this, &StImageViewer::doChangeSwapJPS);
51
params.ToStickPanorama = new StBoolParamNamed(false, stCString("toStickPano360"));
52
params.ToStickPanorama->signals.onChanged = stSlot(this, &StImageViewer::doChangeStickPano360);
53
params.ToFlipCubeZ6x1= new StBoolParamNamed(true, stCString("toFlipCube6x1"));
54
55
params.ToShowFps = new StBoolParamNamed(false, stCString("toShowFps"));
56
params.ToShowMenu = new StBoolParamNamed(true, stCString("toShowMenu"));
57
params.ToShowTopbar = new StBoolParamNamed(true, stCString("toShowTopbar"));
58
+ params.ToShowBottom = new StBoolParamNamed(true, stCString("toShowBottom"));
59
+ params.SlideShowDelay = new StFloat32Param(4.0f, stCString("slideShowDelay2"));
60
+ params.SlideShowDelay->setMinMaxValues(1.0f, 10.0f);
61
+ params.SlideShowDelay->setDefValue(4.0f);
62
+ params.SlideShowDelay->setStep(1.0f);
63
+ params.SlideShowDelay->setTolerance(0.1f);
64
+ params.SlideShowDelay->setFormat(stCString("%01.1f s"));
65
params.IsMobileUI = new StBoolParamNamed(StWindow::isMobile(), stCString("isMobileUI"));
66
params.IsMobileUI->signals.onChanged = stSlot(this, &StImageViewer::doChangeMobileUI);
67
params.IsMobileUISwitch = new StBoolParam(params.IsMobileUI->getValue());
68
69
params.ToHideStatusBar->signals.onChanged = stSlot(this, &StImageViewer::doHideSystemBars);
70
params.ToHideNavBar = new StBoolParamNamed(true, stCString("toHideNavBar"));
71
params.ToHideNavBar ->signals.onChanged = stSlot(this, &StImageViewer::doHideSystemBars);
72
+ params.IsExclusiveFullScreen = new StBoolParamNamed(false, stCString("isExclusiveFullScreen"));
73
params.IsVSyncOn = new StBoolParamNamed(true, stCString("vsync"));
74
params.IsVSyncOn->signals.onChanged = stSlot(this, &StImageViewer::doSwitchVSync);
75
StApplication::params.VSyncMode->setValue(StGLContext::VSync_ON);
76
77
mySettings->loadString(ST_SETTING_LAST_FOLDER, params.lastFolder);
78
mySettings->loadParam (params.LastUpdateDay);
79
mySettings->loadParam (params.CheckUpdatesDays);
80
+ mySettings->loadParam (params.ToSwapJPS);
81
mySettings->loadParam (params.ToStickPanorama);
82
mySettings->loadParam (params.ToFlipCubeZ6x1);
83
mySettings->loadParam (params.ToFlipCubeZ3x2);
84
myToCheckPoorOrient = !mySettings->loadParam(params.ToTrackHead);
85
mySettings->loadParam (params.ToShowFps);
86
+ mySettings->loadParam (params.SlideShowDelay);
87
mySettings->loadParam (params.IsMobileUI);
88
mySettings->loadParam (params.ToHideStatusBar);
89
mySettings->loadParam (params.ToHideNavBar);
90
mySettings->loadParam (params.ToOpenLast);
91
+ mySettings->loadParam (params.IsExclusiveFullScreen);
92
mySettings->loadParam (params.IsVSyncOn);
93
mySettings->loadParam (params.ToShowPlayList);
94
mySettings->loadParam (params.ToShowAdjustImage);
95
96
- int32_t aSlideShowDelayInt = int32_t(mySlideShowDelay);
97
- mySettings->loadInt32 (ST_SETTING_SLIDESHOW_DELAY, aSlideShowDelayInt);
98
- mySlideShowDelay = double(aSlideShowDelayInt);
99
-
100
#if defined(__ANDROID__)
101
addRenderer(new StOutInterlace (myResMgr, theParentWin));
102
addRenderer(new StOutAnaglyph (myResMgr, theParentWin));
103
104
anAction = new StActionBool(stCString("DoShowFPS"), params.ToShowFps);
105
addAction(Action_ShowFps, anAction, ST_VK_F12);
106
107
+ anAction = new StActionIntSlot(stCString("DoShowGUI"), stSlot(this, &StImageViewer::doShowHideGUI), 0);
108
+ addAction(Action_ShowGUI, anAction, ST_VK_TILDE);
109
+
110
anAction = new StActionIntValue(stCString("DoSrcAuto"), params.SrcStereoFormat, StFormat_AUTO);
111
addAction(Action_SrcAuto, anAction, ST_VK_A);
112
113
114
addAction(Action_ListLast, anAction, ST_VK_END);
115
116
anAction = new StActionIntSlot(stCString("DoListPrev"), stSlot(this, &StImageViewer::doListPrev), 0);
117
- addAction(Action_ListPrev, anAction, ST_VK_PRIOR);
118
+ addAction(Action_ListPrev, anAction, ST_VK_PRIOR, StWindow::isMobile() ? ST_VK_VOLUME_UP : 0);
119
120
anAction = new StActionIntSlot(stCString("DoListNext"), stSlot(this, &StImageViewer::doListNext), 0);
121
- addAction(Action_ListNext, anAction, ST_VK_NEXT);
122
+ addAction(Action_ListNext, anAction, ST_VK_NEXT, StWindow::isMobile() ? ST_VK_VOLUME_DOWN : 0);
123
124
anAction = new StActionIntSlot(stCString("DoSlideShow"), stSlot(this, &StImageViewer::doSlideShow), 0);
125
addAction(Action_SlideShow, anAction, ST_VK_SPACE);
126
127
128
anAction = new StActionIntSlot(stCString("DoPanoramaOnOff"), stSlot(this, &StImageViewer::doPanoramaOnOff), 0);
129
addAction(Action_PanoramaOnOff, anAction, ST_VK_P);
130
+
131
+ {
132
+ anAction = new StActionIntSlot(stCString("DoOutStereoNormal"), stSlot(this, &StImageViewer::doSetStereoOutput), StGLImageRegion::MODE_STEREO);
133
+ addAction(Action_OutStereoNormal, anAction);
134
+
135
+ anAction = new StActionIntSlot(stCString("DoOutStereoLeftView"), stSlot(this, &StImageViewer::doSetStereoOutput), StGLImageRegion::MODE_ONLY_LEFT);
136
+ addAction(Action_OutStereoLeftView, anAction);
137
+
138
+ anAction = new StActionIntSlot(stCString("DoOutStereoRightView"), stSlot(this, &StImageViewer::doSetStereoOutput), StGLImageRegion::MODE_ONLY_RIGHT);
139
+ addAction(Action_OutStereoRightView, anAction);
140
+
141
+ anAction = new StActionIntSlot(stCString("DoOutStereoParallelPair"), stSlot(this, &StImageViewer::doSetStereoOutput), StGLImageRegion::MODE_PARALLEL);
142
+ addAction(Action_OutStereoParallelPair, anAction);
143
+
144
+ anAction = new StActionIntSlot(stCString("DoOutStereoCrossEyed"), stSlot(this, &StImageViewer::doSetStereoOutput), StGLImageRegion::MODE_CROSSYED);
145
+ addAction(Action_OutStereoCrossEyed, anAction);
146
+ }
147
}
148
149
bool StImageViewer::resetDevice() {
150
151
mySettings->saveParam (params.ScaleAdjust);
152
mySettings->saveParam (params.ScaleHiDPI2X);
153
mySettings->saveParam (params.TargetFps);
154
- mySettings->saveInt32(ST_SETTING_SLIDESHOW_DELAY, int(mySlideShowDelay));
155
mySettings->saveParam(params.LastUpdateDay);
156
mySettings->saveParam(params.CheckUpdatesDays);
157
mySettings->saveString(ST_SETTING_IMAGELIB, StImageFile::imgLibToString(params.imageLib));
158
+ mySettings->saveParam (params.ToSwapJPS);
159
mySettings->saveParam (params.ToStickPanorama);
160
mySettings->saveParam (params.ToFlipCubeZ6x1);
161
mySettings->saveParam (params.ToFlipCubeZ3x2);
162
mySettings->saveParam (params.ToTrackHead);
163
mySettings->saveParam (params.ToShowFps);
164
+ mySettings->saveParam (params.SlideShowDelay);
165
mySettings->saveParam (params.IsMobileUI);
166
mySettings->saveParam (params.ToHideStatusBar);
167
mySettings->saveParam (params.ToHideNavBar);
168
mySettings->saveParam (params.ToOpenLast);
169
+ mySettings->saveParam (params.IsExclusiveFullScreen);
170
mySettings->saveParam (params.IsVSyncOn);
171
mySettings->saveParam (params.ToShowPlayList);
172
mySettings->saveParam (params.ToShowAdjustImage);
173
174
return false;
175
}
176
myGUI->stglInit();
177
+ StRectF_t aFrustL, aFrustR;
178
+ if(myWindow->getCustomProjection(aFrustL, aFrustR)) {
179
+ myGUI->changeCamera()->setCustomProjection(aFrustL, aFrustR);
180
+ } else {
181
+ myGUI->changeCamera()->resetCustomProjection();
182
+ }
183
myGUI->stglResize(myWindow->stglViewport(ST_WIN_MASTER), myWindow->getMargins(), (float )myWindow->stglAspectRatio());
184
185
for(size_t anIter = 0; anIter < myGUI->myImage->getActions().size(); ++anIter) {
186
187
myGUI->myImage->getTextureQueue(), myContext->getMaxTextureSize());
188
myLoader->signals.onLoaded.connect(this, &StImageViewer::doLoaded);
189
myLoader->setCompressMemory(myWindow->isMobile());
190
+ myLoader->setSwapJPS(params.ToSwapJPS->getValue());
191
myLoader->setStickPano360(params.ToStickPanorama->getValue());
192
myLoader->setFlipCubeZ6x1(params.ToFlipCubeZ6x1->getValue());
193
myLoader->setFlipCubeZ3x2(params.ToFlipCubeZ3x2->getValue());
194
195
// load this parameter AFTER image thread creation
196
mySettings->loadParam(params.SrcStereoFormat);
197
198
-#if !defined(ST_NO_UPDATES_CHECK)
199
+#if defined(ST_UPDATES_CHECK)
200
// read the current time
201
time_t aRawtime;
202
time(&aRawtime);
203
204
if(toMobileGui != wasMobileGui) {
205
doChangeMobileUI(params.IsMobileUI->getValue());
206
} else {
207
+ StRectF_t aFrustL, aFrustR;
208
+ if(myWindow->getCustomProjection(aFrustL, aFrustR)) {
209
+ myGUI->changeCamera()->setCustomProjection(aFrustL, aFrustR);
210
+ } else {
211
+ myGUI->changeCamera()->resetCustomProjection();
212
+ }
213
myGUI->stglResize(myWindow->stglViewport(ST_WIN_MASTER), myWindow->getMargins(), (float )myWindow->stglAspectRatio());
214
}
215
}
216
217
return;
218
}
219
220
+ const bool isReadOnly = StFileNode::isFileReadOnly(myFileToDelete->getPath());
221
const StString aText = myLangMap->getValue(StImageViewerStrings::DIALOG_DELETE_FILE_QUESTION)
222
+ + (isReadOnly ? "\nWARNING! The file is READ ONLY!" : "")
223
+ "\n" + myFileToDelete->getPath();
224
225
StGLMessageBox* aDialog = new StGLMessageBox(myGUI.access(), myLangMap->getValue(StImageViewerStrings::DIALOG_DELETE_FILE_TITLE),
226
227
return;
228
}
229
230
+ StFileNode::removeReadOnlyFlag(myFileToDelete->getPath());
231
myPlayList->removePhysically(myFileToDelete);
232
if(!myPlayList->isEmpty()) {
233
doUpdateStateLoading();
234
235
}
236
237
void StImageViewer::doGesture(const StGestureEvent& theEvent) {
238
- if(myGUI.isNull()
239
- || myGUI->myImage == NULL) {
240
- return;
241
- }
242
-
243
- for(StGLWidget *aChildIter(myGUI->getChildren()->getLast()), *aChildActive(NULL); aChildIter != NULL;) {
244
- aChildActive = aChildIter;
245
- aChildIter = aChildIter->getPrev();
246
- if(aChildActive->isVisibleAndPointIn(myGUI->getCursorZo())) {
247
- if(aChildActive == myGUI->myImage) {
248
- myGUI->myImage->doGesture(theEvent);
249
- }
250
- break;
251
- }
252
+ if(!myGUI.isNull()) {
253
+ myGUI->doGesture(theEvent);
254
}
255
}
256
257
258
}
259
260
const StString aFile1 = theEvent.Files[0];
261
- /*if(!myPlayList->checkExtension(aFile1)) {
262
+ if(!myPlayList->checkExtension(aFile1)
263
+ && myLoader->getMimeListVideo().checkExtension(StFileNode::getExtension(aFile1))) {
264
+ // redirect to StMoviePlayer
265
+ myOpenFileOtherApp = new StOpenInfo();
266
+ StArgumentsMap anArgs;
267
+ anArgs.add(StArgument("in", "video"));
268
+ myOpenFileOtherApp->setArgumentsMap(anArgs);
269
+ myOpenFileOtherApp->setPath(aFile1);
270
+ exit(0);
271
return;
272
- } else */if(theEvent.NbFiles == 1) {
273
+ }
274
+
275
+ if(theEvent.NbFiles == 1) {
276
myPlayList->open(aFile1);
277
doUpdateStateLoading();
278
myLoader->doLoadNext();
279
280
myPlayList->clear();
281
myPlayList->addOneFile(myOpenDialog->getPathLeft(), myOpenDialog->getPathRight());
282
} else {
283
- myPlayList->open(myOpenDialog->getPathLeft());
284
+ if(!myPlayList->checkExtension(myOpenDialog->getPathLeft())
285
+ && myLoader->getMimeListVideo().checkExtension(StFileNode::getExtension(myOpenDialog->getPathLeft()))) {
286
+ // redirect to StMoviePlayer
287
+ myOpenFileOtherApp = new StOpenInfo();
288
+ StArgumentsMap anArgs;
289
+ anArgs.add(StArgument("in", "video"));
290
+ myOpenFileOtherApp->setArgumentsMap(anArgs);
291
+ myOpenFileOtherApp->setPath(myOpenDialog->getPathLeft());
292
+ exit(0);
293
+ } else {
294
+ myPlayList->open(myOpenDialog->getPathLeft());
295
+ }
296
}
297
298
doUpdateStateLoading();
299
300
myLoader->doLoadNext();
301
}
302
303
- if(mySlideShowTimer.getElapsedTimeInSec() > mySlideShowDelay) {
304
+ if(mySlideShowTimer.getElapsedTimeInSec() > params.SlideShowDelay->getValue()) {
305
mySlideShowTimer.restart();
306
doListNext();
307
}
308
309
myGUI->setVisibility(myWindow->getMousePos(), myToHideUIFullScr && isFullScreen);
310
bool toHideCursor = isFullScreen && myGUI->toHideCursor();
311
myWindow->showCursor(!toHideCursor);
312
+
313
+ // for image viewer it is OK to make longer smoothed uploads
314
+ myGUI->myImage->getTextureQueue()->getUploadParams().MaxUploadIterations = 10;
315
}
316
317
void StImageViewer::stglDraw(unsigned int theView) {
318
319
return;
320
}
321
322
+ myLoader->setTheaterMode(theMode == StViewSurface_Theater);
323
+
324
bool isChanged = false;
325
StGLFrameTextures& aTexture = myGUI->myImage->getTextureQueue()->getQTexture().getFront(StGLQuadTexture::LEFT_TEXTURE);
326
if(aTexture.getPlane(0).getTarget() == GL_TEXTURE_CUBE_MAP) {
327
- isChanged = (theMode != StViewSurface_Cubemap);
328
+ isChanged = (theMode != StViewSurface_Cubemap && theMode != StViewSurface_CubemapEAC);
329
} else {
330
- isChanged = (theMode == StViewSurface_Cubemap);
331
+ isChanged = (theMode == StViewSurface_Cubemap || theMode == StViewSurface_CubemapEAC);
332
}
333
334
if(isChanged
335
336
}
337
}
338
339
+void StImageViewer::doSetStereoOutput(const size_t theMode) {
340
+ if(myLoader.isNull()) {
341
+ return;
342
+ }
343
+ myGUI->myImage->params.DisplayMode->setValue((int32_t )theMode);
344
+}
345
+
346
void StImageViewer::doPanoramaOnOff(const size_t ) {
347
if(myLoader.isNull()) {
348
return;
349
350
StPanorama aPano = st::probePanorama(aParams->StereoFormat,
351
aParams->Src1SizeX, aParams->Src1SizeY,
352
aParams->Src2SizeX, aParams->Src2SizeY);
353
- myGUI->myImage->params.ViewMode->setValue(aPano == StPanorama_Cubemap6_1 || aPano == StPanorama_Cubemap3_2
354
- ? StViewSurface_Cubemap
355
- : StViewSurface_Sphere);
356
+ if(aPano == StPanorama_OFF) {
357
+ size_t aSizeX = aParams->Src1SizeX;
358
+ size_t aSizeY = aParams->Src1SizeY;
359
+ StPairRatio aPairRatio = st::formatToPairRatio(aParams->StereoFormat);
360
+ if(aPairRatio == StPairRatio_HalfWidth) {
361
+ aSizeX /= 2;
362
+ } else if(aPairRatio == StPairRatio_HalfHeight) {
363
+ aSizeY /= 2;
364
+ }
365
+ if(aSizeX > 8 && aSizeY > 8) {
366
+ if(double(aSizeX)/double(aSizeY) > 3.5) {
367
+ myGUI->myImage->params.ViewMode->setValue(StViewSurface_Cylinder);
368
+ return;
369
+ }
370
+ }
371
+ }
372
+ myGUI->myImage->params.ViewMode->setValue(StStereoParams::getViewSurfaceForPanoramaSource(aPano, true));
373
+}
374
+
375
+void StImageViewer::doChangeSwapJPS(const bool ) {
376
+ if(!myLoader.isNull()) {
377
+ myLoader->setSwapJPS(params.ToSwapJPS->getValue());
378
+ StHandle<StStereoParams> aParams = myGUI->myImage->getSource();
379
+ if(!aParams.isNull()
380
+ && !myPlayList->isEmpty()) {
381
+ StString aCurrFile = myPlayList->getCurrentTitle();
382
+ aCurrFile.toLowerCase();
383
+ if(aCurrFile.isEndsWith(stCString(".jps"))
384
+ || aCurrFile.isEndsWith(stCString(".pps"))) {
385
+ myLoader->doLoadNext();
386
+ }
387
+ }
388
+ }
389
}
390
391
void StImageViewer::doChangeStickPano360(const bool ) {
392
393
}
394
}
395
396
+void StImageViewer::doShowHideGUI(const size_t ) {
397
+ const bool toShow = !params.ToShowMenu->getValue() || (!myGUI.isNull() && !myGUI->isVisibleGUI());
398
+ params.ToShowMenu->setValue(toShow);
399
+ params.ToShowTopbar->setValue(toShow);
400
+ params.ToShowBottom->setValue(toShow);
401
+ if(toShow && !myGUI.isNull()) {
402
+ myGUI->setVisibility(myWindow->getMousePos(), false, true);
403
+ }
404
+}
405
+
406
void StImageViewer::doSlideShow(const size_t ) {
407
if(mySlideShowTimer.getElapsedTimeInSec() > 0.0) {
408
mySlideShowTimer.stop();
409
410
411
void StImageViewer::doFullscreen(const bool theIsFullscreen) {
412
if(!myWindow.isNull()) {
413
+ myWindow->setAttribute(StWinAttr_ExclusiveFullScreen, params.IsExclusiveFullScreen->getValue());
414
myWindow->setFullScreen(theIsFullscreen);
415
}
416
}
417
sview-17_04.tar.gz/StImageViewer/StImageViewer.h -> sview-20_08.tar.gz/StImageViewer/StImageViewer.h
Changed
83
1
2
/**
3
- * Copyright © 2007-2017 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2007-2020 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* StImageViewer program is free software: you can redistribute it and/or modify
7
* it under the terms of the GNU General Public License as published by
8
9
/**
10
* Reset device - release GL resources in old window and re-create them in new window.
11
*/
12
- ST_CPPEXPORT virtual bool resetDevice();
13
+ ST_CPPEXPORT virtual bool resetDevice() ST_ATTR_OVERRIDE;
14
15
private: //! @name window events slots
16
17
18
ST_LOCAL void doListLast(const size_t dummy = 0);
19
ST_LOCAL void doDeleteFileBegin(const size_t dummy = 0);
20
ST_LOCAL void doDeleteFileEnd(const size_t dummy = 0);
21
+ ST_LOCAL void doShowHideGUI(const size_t dummy = 0);
22
ST_LOCAL void doSlideShow(const size_t dummy = 0);
23
ST_LOCAL void doQuit(const size_t dummy = 0);
24
25
26
StHandle<StEnumParam> CheckUpdatesDays; //!< days count between updates checks
27
StHandle<StInt32ParamNamed> LastUpdateDay; //!< the last time update has been checked
28
StHandle<StInt32ParamNamed> SrcStereoFormat; //!< source format
29
+ StHandle<StBoolParamNamed> ToSwapJPS; //!< swap JPS views order
30
StHandle<StBoolParamNamed> ToStickPanorama; //!< force panorama input for all files
31
StHandle<StBoolParamNamed> ToFlipCubeZ6x1; //!< flip Z coordinate within Cube map 6x1
32
StHandle<StBoolParamNamed> ToFlipCubeZ3x2; //!< flip Z coordinate within Cube map 3x2
33
StHandle<StBoolParamNamed> ToTrackHead; //!< enable/disable head-tracking
34
StHandle<StBoolParamNamed> ToShowMenu; //!< show main menu
35
StHandle<StBoolParamNamed> ToShowTopbar; //!< show topbar
36
+ StHandle<StBoolParamNamed> ToShowBottom; //!< show bottom
37
StHandle<StBoolParamNamed> ToShowPlayList; //!< display playlist
38
StHandle<StBoolParamNamed> ToShowAdjustImage;//!< display image adjustment overlay
39
StHandle<StBoolParamNamed> ToShowFps; //!< display FPS meter
40
+ StHandle<StFloat32Param> SlideShowDelay; //!< slideshow delay
41
StHandle<StBoolParamNamed> IsMobileUI; //!< display mobile interface (user option)
42
StHandle<StBoolParam> IsMobileUISwitch; //!< display mobile interface (actual value)
43
StHandle<StBoolParamNamed> ToHideStatusBar; //!< hide system-provided status bar
44
StHandle<StBoolParamNamed> ToHideNavBar; //!< hide system-provided navigation bar
45
+ StHandle<StBoolParamNamed> IsExclusiveFullScreen; //!< exclusive fullscreen mode
46
StHandle<StBoolParamNamed> IsVSyncOn; //!< flag to use VSync
47
StHandle<StBoolParamNamed> ToOpenLast; //!< option to open last file from recent list by default
48
StHandle<StBoolParamNamed> ToSaveRecent; //!< load/save recent file
49
50
ST_LOCAL void doFullscreen(const bool theIsFullscreen);
51
ST_LOCAL void doSwitchSrcFormat(const int32_t theSrcFormat);
52
ST_LOCAL void doSwitchViewMode(const int32_t theMode);
53
+ ST_LOCAL void doSetStereoOutput(const size_t theMode);
54
ST_LOCAL void doPanoramaOnOff(const size_t );
55
+ ST_LOCAL void doChangeSwapJPS(const bool );
56
ST_LOCAL void doChangeStickPano360(const bool );
57
ST_LOCAL void doChangeFlipCubeZ(const bool );
58
ST_LOCAL void doShowPlayList(const bool theToShow);
59
60
Action_StereoParamsBegin,
61
Action_StereoParamsEnd = Action_StereoParamsBegin + StGLImageRegion::ActionsNb - 1,
62
Action_PanoramaOnOff,
63
+ Action_ShowGUI,
64
+ Action_OutStereoNormal,
65
+ Action_OutStereoLeftView,
66
+ Action_OutStereoRightView,
67
+ Action_OutStereoParallelPair,
68
+ Action_OutStereoCrossEyed,
69
};
70
71
private:
72
73
74
StCondition myEventLoaded; //!< indicate that new file was open
75
StTimer myInactivityTimer; //!< timer initialized when application goes into paused state
76
-
77
- StTimer mySlideShowTimer; //!< slideshow stuff
78
- double mySlideShowDelay;
79
+ StTimer mySlideShowTimer; //!< slideshow timer
80
81
bool myToCheckUpdates;
82
bool myToSaveSrcFormat; //!< indicates that active source format should be saved or not
83
sview-17_04.tar.gz/StImageViewer/StImageViewer.rc -> sview-20_08.tar.gz/StImageViewer/StImageViewer.rc
Changed
10
1
2
BEGIN
3
VALUE "FileDescription", "Stereoscopic Image Viewer\000"
4
VALUE "FileVersion", SVIEW_SDK_VER_STRING "\000"
5
- VALUE "LegalCopyright", "\251 2007-2017 Kirill Gavrilov\000"
6
+ VALUE "LegalCopyright", "\251 2007-2020 Kirill Gavrilov and sView developers\000"
7
VALUE "ProductName", "StImageViewer\000"
8
VALUE "ProductVersion", SVIEW_SDK_VER_STRING "\000"
9
VALUE "OfficialSite", "www.sview.ru\000"
10
sview-17_04.tar.gz/StImageViewer/StImageViewerGUI.cpp -> sview-20_08.tar.gz/StImageViewer/StImageViewerGUI.cpp
Changed
363
1
2
/**
3
- * Copyright © 2009-2017 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2009-2020 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* StImageViewer program is free software: you can redistribute it and/or modify
7
* it under the terms of the GNU General Public License as published by
8
9
10
namespace {
11
12
+ static const float THE_VISIBILITY_IDLE_TIME = 2.0f;
13
+
14
static const int DISPL_Y_REGION_UPPER = 32;
15
static const int DISPL_X_REGION_UPPER = 32;
16
17
18
const int anIconStep = scale(48);
19
aButtonMargins.extend(scale(8));
20
21
- myPanelUpper = new StGLContainer(this, 0, 0, StGLCorner(ST_VCORNER_TOP, ST_HCORNER_LEFT), scale(4096), scale(128));
22
+ myPanelUpper = new StGLContainer(this, aLeft, aTop, StGLCorner(ST_VCORNER_TOP, ST_HCORNER_LEFT), scale(4096), scale(128));
23
24
// append textured buttons
25
- myBtnOpen = new StGLTextureButton(myPanelUpper, aLeft + (aBtnIter++) * anIconStep, aTop);
26
+ myBtnOpen = new StGLTextureButton(myPanelUpper, (aBtnIter++) * anIconStep, 0);
27
myBtnOpen->signals.onBtnClick.connect(myPlugin, &StImageViewer::doOpen1FileAction);
28
myBtnOpen->setTexturePath(iconTexture(stCString("actionOpen"), anIconSize));
29
myBtnOpen->setDrawShadow(true);
30
myBtnOpen->changeMargins() = aButtonMargins;
31
32
- myBtnPrev = new StGLTextureButton(myPanelUpper, aLeft + (aBtnIter++) * anIconStep, aTop);
33
+ myBtnPrev = new StGLTextureButton(myPanelUpper, (aBtnIter++) * anIconStep, 0);
34
myBtnPrev->signals.onBtnClick.connect(myPlugin, &StImageViewer::doListPrev);
35
myBtnPrev->setTexturePath(iconTexture(stCString("actionBack"), anIconSize));
36
myBtnPrev->setDrawShadow(true);
37
myBtnPrev->changeMargins() = aButtonMargins;
38
39
- myBtnNext = new StGLTextureButton(myPanelUpper, aLeft + (aBtnIter++) * anIconStep, aTop);
40
+ myBtnNext = new StGLTextureButton(myPanelUpper, (aBtnIter++) * anIconStep, 0);
41
myBtnNext->signals.onBtnClick.connect(myPlugin, &StImageViewer::doListNext);
42
myBtnNext->setTexturePath(iconTexture(stCString("actionNext"), anIconSize));
43
myBtnNext->setDrawShadow(true);
44
myBtnNext->changeMargins() = aButtonMargins;
45
46
- myBtnInfo = new StGLTextureButton(myPanelUpper, aLeft + (aBtnIter++) * anIconStep, aTop);
47
+ myBtnInfo = new StGLTextureButton(myPanelUpper, (aBtnIter++) * anIconStep, 0);
48
myBtnInfo->signals.onBtnClick += stSlot(myPlugin, &StImageViewer::doAboutImage);
49
myBtnInfo->setTexturePath(iconTexture(stCString("actionInfo"), anIconSize));
50
myBtnInfo->setDrawShadow(true);
51
myBtnInfo->changeMargins() = aButtonMargins;
52
53
- StGLTextureButton* aSrcBtn = new StGLTextureButton(myPanelUpper, aLeft + (aBtnIter++) * anIconStep, aTop,
54
+ StGLTextureButton* aSrcBtn = new StGLTextureButton(myPanelUpper, (aBtnIter++) * anIconStep, 0,
55
StGLCorner(ST_VCORNER_TOP, ST_HCORNER_LEFT), StFormat_NB);
56
aSrcBtn->changeMargins() = aButtonMargins;
57
aSrcBtn->signals.onBtnClick += stSlot(this, &StImageViewerGUI::doDisplayStereoFormatCombo);
58
59
myBtnSwapLR = new StGLCheckboxTextured(myPanelUpper, myImage->params.SwapLR,
60
iconTexture(stCString("actionSwapLROff"), anIconSize),
61
iconTexture(stCString("actionSwapLROn"), anIconSize),
62
- aLeft + (aBtnIter++) * anIconStep, aTop,
63
+ (aBtnIter++) * anIconStep, 0,
64
StGLCorner(ST_VCORNER_TOP, ST_HCORNER_LEFT));
65
myBtnSwapLR->setDrawShadow(true);
66
myBtnSwapLR->changeMargins() = aButtonMargins;
67
68
myBtnPanorama = new StGLCheckboxTextured(myPanelUpper, aTrackedPano,
69
iconTexture(stCString("actionPanoramaOff"), anIconSize),
70
iconTexture(stCString("actionPanorama"), anIconSize),
71
- aLeft + (aBtnIter++) * anIconStep, aTop,
72
+ (aBtnIter++) * anIconStep, 0,
73
StGLCorner(ST_VCORNER_TOP, ST_HCORNER_LEFT));
74
myBtnPanorama->signals.onBtnClick += stSlot(this, &StImageViewerGUI::doPanoramaCombo);
75
myBtnPanorama->setDrawShadow(true);
76
77
myBtnAdjust = new StGLCheckboxTextured(myPanelUpper, myPlugin->params.ToShowAdjustImage,
78
iconTexture(stCString("actionColorAdjustOff"), anIconSize),
79
iconTexture(stCString("actionColorAdjust"), anIconSize),
80
- aLeft + (aBtnIter++) * anIconStep, aTop,
81
+ (aBtnIter++) * anIconStep, 0,
82
StGLCorner(ST_VCORNER_TOP, ST_HCORNER_LEFT));
83
myBtnAdjust->setDrawShadow(true);
84
myBtnAdjust->changeMargins() = aButtonMargins;
85
86
void StImageViewerGUI::fillPanoramaMenu(StGLMenu* theMenu) {
87
theMenu->addItem(tr(MENU_VIEW_SURFACE_PLANE),
88
myImage->params.ViewMode, StViewSurface_Plain);
89
+ theMenu->addItem(tr(MENU_VIEW_SURFACE_THEATER),
90
+ myImage->params.ViewMode, StViewSurface_Theater);
91
+ theMenu->addItem(tr(MENU_VIEW_SURFACE_CYLINDER),
92
+ myImage->params.ViewMode, StViewSurface_Cylinder);
93
+ theMenu->addItem(tr(MENU_VIEW_SURFACE_HEMISPHERE),
94
+ myImage->params.ViewMode, StViewSurface_Hemisphere);
95
theMenu->addItem(tr(MENU_VIEW_SURFACE_SPHERE),
96
myImage->params.ViewMode, StViewSurface_Sphere);
97
theMenu->addItem(tr(MENU_VIEW_SURFACE_CUBEMAP),
98
myImage->params.ViewMode, StViewSurface_Cubemap);
99
+ theMenu->addItem(tr(MENU_VIEW_SURFACE_CUBEMAP_EAC),
100
+ myImage->params.ViewMode, StViewSurface_CubemapEAC);
101
if(myWindow->hasOrientationSensor()) {
102
theMenu->addItem(tr(myWindow->isPoorOrientationSensor() ? MENU_VIEW_TRACK_HEAD_POOR : MENU_VIEW_TRACK_HEAD),
103
myPlugin->params.ToTrackHead);
104
105
myImage->params.TextureFilter, StGLImageProgram::FILTER_NEAREST);
106
aMenu->addItem(tr(MENU_VIEW_TEXFILTER_LINEAR),
107
myImage->params.TextureFilter, StGLImageProgram::FILTER_LINEAR);
108
+ aMenu->addItem(tr(MENU_VIEW_TEXFILTER_TRILINEAR),
109
+ myImage->params.TextureFilter, StGLImageProgram::FILTER_TRILINEAR);
110
return aMenu;
111
}
112
113
114
const StGLVec3 THE_WHITE(1.0f, 1.0f, 1.0f);
115
const StString anAbout = tr(ABOUT_DPLUGIN_NAME) + '\n'
116
+ tr(ABOUT_VERSION) + " " + StVersionInfo::getSDKVersionString()
117
- + "\n \n" + tr(ABOUT_DESCRIPTION).format("2007-2017", "kirill@sview.ru", "www.sview.ru");
118
+ + "\n \n" + tr(ABOUT_DESCRIPTION).format("2007-2020", "kirill@sview.ru", "www.sview.ru");
119
120
StArgumentsMap anInfo;
121
anInfo.add(StDictEntry("CPU cores", StString(StThread::countLogicalProcessors()) + StString(" logical processor(s)")));
122
123
aParams.add(myPlugin->params.ToStickPanorama);
124
aParams.add(myPlugin->params.ToFlipCubeZ6x1);
125
aParams.add(myPlugin->params.ToFlipCubeZ3x2);
126
+ aParams.add(myPlugin->params.ToSwapJPS);
127
aParams.add(myPlugin->params.ToShowFps);
128
+ aParams.add(myPlugin->params.SlideShowDelay);
129
aParams.add(myLangMap->params.language);
130
aParams.add(myPlugin->params.IsMobileUI);
131
+#if defined(_WIN32) || defined(__APPLE__) // implemented only on Windows and macOS
132
+ aParams.add(myPlugin->params.IsExclusiveFullScreen);
133
+#endif
134
if(isMobile()) {
135
//aParams.add(myPlugin->params.ToHideStatusBar);
136
aParams.add(myPlugin->params.ToHideNavBar);
137
138
aParams.add(myPlugin->params.ToOpenLast);
139
}
140
aParams.add(myPlugin->params.ExitOnEscape);
141
-#if !defined(ST_NO_UPDATES_CHECK)
142
+#if defined(ST_UPDATES_CHECK)
143
aParams.add(myPlugin->params.CheckUpdatesDays);
144
#endif
145
146
+ if(!myWindow->isMobile()) {
147
+ StHandle<StBoolParamNamed> aDefDrawerParam = myPlugin->createDefaultDrawerParam(stCString("StImageViewer"),
148
+ stCString("sView launcher starts Image Viewer"));
149
+ aParams.add(aDefDrawerParam);
150
+ }
151
+
152
StInfoDialog* aDialog = new StInfoDialog(myPlugin, this, tr(MENU_HELP_SETTINGS), scale(768), scale(300));
153
154
const int aWidthMax = aDialog->getContent()->getRectPx().width();
155
156
157
void StImageViewerGUI::doOpenFile(const size_t ) {
158
StGLOpenFile* aDialog = new StGLOpenFile(this, tr(DIALOG_OPEN_FILE), tr(BUTTON_CLOSE));
159
- aDialog->setMimeList(myPlugin->myLoader->getMimeList());
160
-#if defined(_WIN32)
161
- //
162
-#else
163
- aDialog->addHotItem("/", "Root");
164
-#endif
165
- aDialog->addHotItem(getResourceManager()->getFolder(StResourceManager::FolderId_SdCard));
166
+
167
+ const StString anSdCardPath = getResourceManager()->getFolder(StResourceManager::FolderId_SdCard);
168
+ if(!anSdCardPath.isEmpty()) {
169
+ StString aFolder, aName;
170
+ StFileNode::getFolderAndFile(anSdCardPath, aFolder, aName);
171
+ aDialog->addHotItem(anSdCardPath, stUtfTools::isInteger(aName) ? (StString("sdcard") + aName) : aName);
172
+ }
173
aDialog->addHotItem(getResourceManager()->getFolder(StResourceManager::FolderId_Downloads));
174
+ aDialog->addHotItem(getResourceManager()->getFolder(StResourceManager::FolderId_Documents));
175
aDialog->addHotItem(getResourceManager()->getFolder(StResourceManager::FolderId_Pictures));
176
aDialog->addHotItem(getResourceManager()->getFolder(StResourceManager::FolderId_Photos));
177
aDialog->signals.onFileSelected = stSlot(myPlugin, &StImageViewer::doOpen1FileFromGui);
178
179
+ aDialog->setMimeList(myPlugin->myLoader->getMimeListImages(), "Images", false);
180
+ aDialog->setMimeList(myPlugin->myLoader->getMimeListVideo(), "Videos", true);
181
+
182
if(myPlugin->params.lastFolder.isEmpty()) {
183
StHandle<StFileNode> aCurrFile = myPlugin->myPlayList->getCurrentFile();
184
if(!aCurrFile.isNull()) {
185
186
}
187
188
myImage = new StGLImageRegion(this, aTextureQueue, true);
189
+ myImage->changeIconPrev()->setTexturePath(iconTexture(stCString("actionBack"), scaleIcon(64)));
190
+ myImage->changeIconPrev()->setDrawShadow(true);
191
+ myImage->changeIconNext()->setTexturePath(iconTexture(stCString("actionNext"), scaleIcon(64)));
192
+ myImage->changeIconNext()->setDrawShadow(true);
193
+ myImage->signals.onOpenItem = stSlot(myPlugin, &StImageViewer::doFileNext);
194
+ myImage->setPlayList(thePlayList);
195
myImage->params.DisplayMode->setName(tr(MENU_VIEW_DISPLAY_MODE));
196
myImage->params.DisplayMode->changeValues()[StGLImageRegion::MODE_STEREO] = tr(MENU_VIEW_DISPLAY_MODE_STEREO);
197
myImage->params.DisplayMode->changeValues()[StGLImageRegion::MODE_ONLY_LEFT] = tr(MENU_VIEW_DISPLAY_MODE_LEFT);
198
199
}
200
}
201
202
+void StImageViewerGUI::doGesture(const StGestureEvent& theEvent) {
203
+ if(myImage == NULL) {
204
+ return;
205
+ }
206
+
207
+ if(theEvent.Type == stEvent_Gesture1Tap) {
208
+ myTapTimer.restart();
209
+ } else if(theEvent.Type == stEvent_Gesture1DoubleTap) {
210
+ myTapTimer.stop();
211
+ }
212
+
213
+ for(StGLWidget *aChildIter(getChildren()->getLast()), *aChildActive(NULL); aChildIter != NULL;) {
214
+ aChildActive = aChildIter;
215
+ aChildIter = aChildIter->getPrev();
216
+ if(aChildActive->isVisibleAndPointIn(getCursorZo())) {
217
+ if(aChildActive == myImage) {
218
+ myImage->doGesture(theEvent);
219
+ }
220
+ return;
221
+ }
222
+ }
223
+}
224
+
225
void StImageViewerGUI::setVisibility(const StPointD_t& theCursor,
226
- bool toForceHide) {
227
+ bool theToForceHide,
228
+ bool theToForceShow) {
229
const bool toShowAdjust = myPlugin->params.ToShowAdjustImage->getValue();
230
const bool toShowPlayList = myPlugin->params.ToShowPlayList->getValue();
231
const bool hasMainMenu = myPlugin->params.ToShowMenu->getValue()
232
233
&& myPlugin->params.ToShowTopbar->getValue()
234
&& myPanelUpper != NULL;
235
const bool hasBottomPanel = !myIsMinimalGUI
236
+ && myPlugin->params.ToShowBottom->getValue()
237
&& myPanelBottom != NULL;
238
- const bool isMouseActive = myWindow->isMouseMoved();
239
240
StHandle<StStereoParams> aParams = myImage->getSource();
241
+ if(aParams.isNull() && !myEmptyTimer.isOn()
242
+ && !myPlugin->myPlayList->isEmpty()) {
243
+ myEmptyTimer.restart();
244
+ } else {
245
+ myEmptyTimer.stop();
246
+ }
247
+ if(myEmptyTimer.getElapsedTime() >= 2.5) {
248
+ myVisibilityTimer.restart();
249
+ myEmptyTimer.stop();
250
+ }
251
+ if(myTapTimer.getElapsedTime() >= 0.5) {
252
+ myVisibilityTimer.restart();
253
+ myTapTimer.stop();
254
+ }
255
+ if(theToForceShow) {
256
+ myVisibilityTimer.restart();
257
+ }
258
+ const bool isMouseActive = myWindow->isMouseMoved();
259
+
260
StFormat aSrcFormat = (StFormat )myPlugin->params.SrcStereoFormat->getValue();
261
if(aSrcFormat == StFormat_AUTO
262
&& !aParams.isNull()) {
263
264
265
const double aStillTime = myVisibilityTimer.getElapsedTime();
266
myIsVisibleGUI = isMouseActive
267
- || aParams.isNull()
268
- || aStillTime < 2.0
269
+ || aStillTime < THE_VISIBILITY_IDLE_TIME
270
|| (hasUpperPanel && myPanelUpper ->isPointIn(theCursor))
271
|| (hasBottomPanel && myPanelBottom->isPointIn(theCursor))
272
|| (myPlayList != NULL && toShowPlayList && myPlayList->isPointIn(theCursor))
273
274
if(isMouseActive) {
275
myVisibilityTimer.restart();
276
}
277
- const bool toShowAll = !myIsMinimalGUI && myIsVisibleGUI && !toForceHide;
278
- const float anOpacity = (float )myVisLerp.perform(toShowAll, toForceHide);
279
+ const bool toShowAll = !myIsMinimalGUI && myIsVisibleGUI && !theToForceHide;
280
+ const float anOpacity = (float )myVisLerp.perform(toShowAll, theToForceHide || theToForceShow);
281
282
if(myMenuRoot != NULL) {
283
myMenuRoot->setOpacity(hasMainMenu ? anOpacity : 0.0f, true);
284
285
}
286
if(myPlayList != NULL
287
&& toShowPlayList) {
288
- myPlayList->setOpacity(anOpacity, true);
289
+ myPlayList->setOpacity(myPlugin->params.ToShowBottom->getValue() ? anOpacity : 0.0f, true);
290
}
291
if(myBtnFull != NULL) {
292
if(myIsMinimalGUI
293
294
bool toShowPano = aViewMode != StViewSurface_Plain;
295
if(!toShowPano
296
&& !aParams.isNull()
297
- && st::probePanorama(aParams->StereoFormat,
298
+ /*&& st::probePanorama(aParams->StereoFormat,
299
aParams->Src1SizeX, aParams->Src1SizeY,
300
- aParams->Src2SizeX, aParams->Src2SizeY) != StPanorama_OFF) {
301
+ aParams->Src2SizeX, aParams->Src2SizeY) != StPanorama_OFF*/) {
302
toShowPano = true;
303
}
304
if(myBtnPanorama != NULL) {
305
306
} else if(::isPointIn(myBtnPanorama, theCursor)) {
307
size_t aTrPano = MENU_VIEW_SURFACE_PLANE;
308
switch(aViewMode) {
309
- case StViewSurface_Plain: aTrPano = MENU_VIEW_SURFACE_PLANE; break;
310
- case StViewSurface_Sphere: aTrPano = MENU_VIEW_SURFACE_SPHERE; break;
311
- case StViewSurface_Cubemap: aTrPano = MENU_VIEW_SURFACE_CUBEMAP; break;
312
+ case StViewSurface_Plain: aTrPano = MENU_VIEW_SURFACE_PLANE; break;
313
+ case StViewSurface_Theater: aTrPano = MENU_VIEW_SURFACE_THEATER; break;
314
+ case StViewSurface_Sphere: aTrPano = MENU_VIEW_SURFACE_SPHERE; break;
315
+ case StViewSurface_Hemisphere: aTrPano = MENU_VIEW_SURFACE_HEMISPHERE; break;
316
+ case StViewSurface_Cubemap: aTrPano = MENU_VIEW_SURFACE_CUBEMAP; break;
317
+ case StViewSurface_CubemapEAC: aTrPano = MENU_VIEW_SURFACE_CUBEMAP_EAC; break;
318
+ case StViewSurface_Cylinder: aTrPano = MENU_VIEW_SURFACE_CYLINDER; break;
319
}
320
myDescr->setText(tr(MENU_VIEW_PANORAMA) + "\n" + tr(aTrPano));
321
} else {
322
323
float theAspect) {
324
const int aNewSizeX = theViewPort.width();
325
const int aNewSizeY = theViewPort.height();
326
- const int aWorkRight = stMax(aNewSizeX - theMargins.right - theMargins.left, 2);
327
+ int aGapTopX = 0, aGapTopY = 0, aGapBotX = 0, aGapBotY = 0;
328
+ if(isMobile()) {
329
+ // add gap for hidden system navigation buttons
330
+ static const int THE_NAVIGATION_GAPX = 32;
331
+ static const int THE_NAVIGATION_GAPY = 16;
332
+ if(theAspect < 9.0 / 16.0 && theAspect > 0.0) {
333
+ aGapTopY = aGapBotY = stMax(0, scale(stMin(THE_NAVIGATION_GAPY, int((1.0 / theAspect * 360) - 360 * 2))));
334
+ } else if(theAspect > 9.0 / 16.0) {
335
+ aGapTopX = aGapBotX = stMax(0, scale(stMin(THE_NAVIGATION_GAPX, int((theAspect * 360) - 360 * 2))));
336
+ }
337
+ } else {
338
+ aGapTopY = scale(DISPL_Y_REGION_UPPER);
339
+ aGapTopX = scale(DISPL_X_REGION_UPPER);
340
+ }
341
342
// image should fit entire view
343
myImage->changeRectPx().top() = -theMargins.top;
344
345
myImage->changeRectPx().right() = -theMargins.left + aNewSizeX;
346
347
if(myPanelUpper != NULL) {
348
- myPanelUpper->changeRectPx().right() = aWorkRight;
349
+ myPanelUpper->changeRectPx().top() = aGapTopY;
350
+ myPanelUpper->changeRectPx().left() = aGapTopX;
351
+ myPanelUpper->changeRectPx().right() = aGapTopX + stMax(aNewSizeX - theMargins.right - theMargins.left - 2 * aGapTopX, 2);
352
myIsMinimalGUI = (myWindow->isMovable() || myWindow->hasFullscreenMode()) && !isMobile()
353
&& (aNewSizeY < scale(400) || aNewSizeX < scale(400));
354
}
355
if(myPanelBottom != NULL) {
356
- myPanelBottom->changeRectPx().right() = aWorkRight;
357
+ myPanelBottom->changeRectPx().top() = -aGapBotY;
358
+ myPanelBottom->changeRectPx().left() = aGapBotX;
359
+ myPanelBottom->changeRectPx().right() = aGapBotX + stMax(aNewSizeX - theMargins.right - theMargins.left - 2 * aGapBotX, 2);
360
}
361
StGLRootWidget::stglResize(theViewPort, theMargins, theAspect);
362
}
363
sview-17_04.tar.gz/StImageViewer/StImageViewerGUI.h -> sview-20_08.tar.gz/StImageViewer/StImageViewerGUI.h
Changed
33
1
2
/**
3
- * Copyright © 2009-2017 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2009-2020 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* StImageViewer program is free software: you can redistribute it and/or modify
7
* it under the terms of the GNU General Public License as published by
8
9
float theAspect) ST_ATTR_OVERRIDE;
10
ST_LOCAL virtual void stglDraw(unsigned int theView) ST_ATTR_OVERRIDE;
11
12
+ /**
13
+ * Handle gesture.
14
+ */
15
+ ST_LOCAL void doGesture(const StGestureEvent& theEvent);
16
+ ST_LOCAL bool isVisibleGUI() const { return myVisLerp.getValue() > 0.0; }
17
ST_LOCAL void setVisibility(const StPointD_t& theCursor,
18
- bool toForceHide);
19
+ bool theToForceHide,
20
+ bool theToForceShow = false);
21
22
public:
23
24
25
StWindow* myWindow; //!< link to the window instance
26
StTranslations* myLangMap; //!< translated strings map
27
StTimer myVisibilityTimer; //!< minimum visible delay
28
+ StTimer myEmptyTimer; //!< empty list delay
29
+ StTimer myTapTimer; //!< single tap delay
30
StGLAnimationLerp myVisLerp;
31
32
StGLImageRegion* myImage; //!< the main image
33
sview-17_04.tar.gz/StImageViewer/StImageViewerStrings.cpp -> sview-20_08.tar.gz/StImageViewer/StImageViewerStrings.cpp
Changed
77
1
2
/**
3
- * Copyright © 2013-2017 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2013-2020 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* StImageViewer program is free software: you can redistribute it and/or modify
7
* it under the terms of the GNU General Public License as published by
8
9
"Plane");
10
theStrings(MENU_VIEW_SURFACE_SPHERE,
11
"Sphere");
12
+ theStrings(MENU_VIEW_SURFACE_HEMISPHERE,
13
+ "Hemisphere");
14
theStrings(MENU_VIEW_SURFACE_CYLINDER,
15
"Cylinder");
16
theStrings(MENU_VIEW_SURFACE_CUBEMAP,
17
"Cubemap");
18
+ theStrings(MENU_VIEW_SURFACE_THEATER,
19
+ "Theater");
20
+ theStrings(MENU_VIEW_SURFACE_CUBEMAP_EAC,
21
+ "Equiangular cubemap");
22
theStrings(MENU_VIEW_TRACK_HEAD,
23
"Track orientation");
24
theStrings(MENU_VIEW_TRACK_HEAD_POOR,
25
26
"Nearest");
27
theStrings(MENU_VIEW_TEXFILTER_LINEAR,
28
"Linear"),
29
+ theStrings(MENU_VIEW_TEXFILTER_TRILINEAR,
30
+ "Trilinear"),
31
theStrings(MENU_CHANGE_DEVICE,
32
"Change Device");
33
theStrings(MENU_ABOUT_RENDERER,
34
35
"Show FPS");
36
theStrings(MENU_VSYNC,
37
"VSync");
38
+ theStrings(MENU_EXCLUSIVE_FULLSCREEN,
39
+ "Exclusive Fullscreen mode");
40
theStrings(ABOUT_DPLUGIN_NAME,
41
"sView - Image Viewer");
42
theStrings(ABOUT_VERSION,
43
44
"Hide system navigation bar");
45
theStrings(OPTION_OPEN_LAST_ON_STARTUP,
46
"Open last viewed file on startup");
47
+ theStrings(OPTION_SWAP_JPS,
48
+ "Swap JPS/PNS views order");
49
50
theStrings(UPDATES_NOTIFY,
51
"A new version of sView is available on the official site www.sview.ru.\n"
52
53
"msec");
54
theStrings(INFO_PIXEL_RATIO,
55
"Pixel ratio");
56
+ theStrings(INFO_PIXEL_FORMAT,
57
+ "Pixel format");
58
theStrings(INFO_COLOR_MODEL,
59
"Color model");
60
theStrings(INFO_NO_SRCFORMAT,
61
62
addAction(theStrings, StImageViewer::Action_PanoramaOnOff,
63
"DoPanoramaOnOff",
64
"Enable/disable panorama mode");
65
+ addAction(theStrings, StImageViewer::Action_ShowGUI,
66
+ "DoShowGUI",
67
+ "Show/hide GUI");
68
+
69
+ theStrings.addAlias("DoOutStereoNormal", MENU_VIEW_DISPLAY_MODE_STEREO);
70
+ theStrings.addAlias("DoOutStereoLeftView", MENU_VIEW_DISPLAY_MODE_LEFT);
71
+ theStrings.addAlias("DoOutStereoRightView", MENU_VIEW_DISPLAY_MODE_RIGHT);
72
+ theStrings.addAlias("DoOutStereoParallelPair", MENU_VIEW_DISPLAY_MODE_PARALLEL);
73
+ theStrings.addAlias("DoOutStereoCrossEyed", MENU_VIEW_DISPLAY_MODE_CROSSYED);
74
}
75
76
};
77
sview-17_04.tar.gz/StImageViewer/StImageViewerStrings.h -> sview-20_08.tar.gz/StImageViewer/StImageViewerStrings.h
Changed
59
1
2
/**
3
- * Copyright © 2009-2017 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2009-2020 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* StImageViewer program is free software: you can redistribute it and/or modify
7
* it under the terms of the GNU General Public License as published by
8
9
10
MENU_VIEW_TEXFILTER_NEAREST = 1260,
11
MENU_VIEW_TEXFILTER_LINEAR = 1261,
12
+ MENU_VIEW_TEXFILTER_TRILINEAR = 1263,
13
14
MENU_VIEW_ADJUST_RESET = 1270,
15
MENU_VIEW_ADJUST_BRIGHTNESS = 1271,
16
17
MENU_VIEW_SURFACE_SPHERE = 1281,
18
MENU_VIEW_SURFACE_CYLINDER = 1282,
19
MENU_VIEW_SURFACE_CUBEMAP = 1283,
20
+ MENU_VIEW_SURFACE_HEMISPHERE= 1284,
21
MENU_VIEW_TRACK_HEAD = 1285,
22
MENU_VIEW_TRACK_HEAD_POOR = 1286,
23
MENU_VIEW_STICK_PANORAMA360 = 1288,
24
MENU_VIEW_FLIPZ_CUBE6x1 = 1291,
25
MENU_VIEW_FLIPZ_CUBE3x2 = 1292,
26
+ MENU_VIEW_SURFACE_CUBEMAP_EAC = 1293,
27
+ MENU_VIEW_SURFACE_THEATER = 1294,
28
29
// Root -> Output -> Change Device menu
30
MENU_CHANGE_DEVICE = 1400,
31
MENU_ABOUT_RENDERER = 1401,
32
MENU_SHOW_FPS = 1402,
33
MENU_VSYNC = 1403,
34
+ MENU_EXCLUSIVE_FULLSCREEN = 1404,
35
36
// Root -> Help menu
37
MENU_HELP = 1500,
38
39
OPTION_EXIT_ON_ESCAPE_WINDOWED = 1705,
40
OPTION_HIDE_NAVIGATION_BAR = 1710,
41
OPTION_OPEN_LAST_ON_STARTUP = 1711,
42
+ OPTION_SWAP_JPS = 1712,
43
44
// Open/Save dialogs
45
DIALOG_OPEN_FILE = 2000,
46
47
INFO_LOAD_TIME = 5004,
48
INFO_TIME_MSEC = 5005,
49
INFO_PIXEL_RATIO = 5006,
50
- INFO_COLOR_MODEL = 5007,
51
+ INFO_PIXEL_FORMAT = 5007,
52
INFO_NO_SRCFORMAT = 5008,
53
INFO_WRONG_SRCFORMAT = 5009,
54
INFO_NO_SRCFORMAT_EX = 5011,
55
+ INFO_COLOR_MODEL = 5012,
56
57
// metadata keys
58
METADATA_JPEG_COMMENT = 5100,
59
sview-17_04.tar.gz/StImageViewer/lang/chinese/StImageViewer.lng -> sview-20_08.tar.gz/StImageViewer/lang/chinese/StImageViewer.lng
Changed
50
1
2
?1252=Heal anamorphic 1080p/720p
3
1260=接近
4
1261=线状
5
+?1263=Trilinear
6
1270=重置默认
7
1271=亮度
8
1272=饱和度
9
10
1281=球面
11
1282=圆柱
12
?1283=Cubemap
13
+?1284=Hemisphere
14
?1285=Track orientation
15
?1286=Track orientation (poor)
16
?1288=Stick at panorama 360°
17
?1291=Cubemap 6x1 - flip Z
18
?1292=Cubemap 3x2 - flip Z
19
+?1293=Equiangular cubemap
20
+?1294=Theater
21
1400=改变设备
22
1401=关于插件...
23
1402=显示 FPS
24
1403=同步
25
+?1404=Exclusive Fullscreen mode
26
1500=帮助
27
1501=关于...
28
1502=更新检查
29
30
?1705=On one click windowed mode
31
?1710=Hide system navigation bar
32
?1711=Open last viewed file on startup
33
+?1712=Swap JPS/PNS views order
34
2000=选择图片文件打开
35
2001=选择左画面图片打开
36
2002=选择右画面图片文件打开
37
38
5008=(不存储在元数据)
39
5009=(不匹配的元数据)
40
5011=(不存储在元数据中,\n但检测到文件名称)
41
+?5012=Color model
42
5100=JPEG 说明
43
5101=JPS 说明
44
5200=相机生产商
45
46
?6040=X Rotation - up
47
?6041=X Rotation - down
48
?6042=Enable/disable panorama mode
49
+?6043=Show/hide GUI
50
sview-17_04.tar.gz/StImageViewer/lang/czech/StImageViewer.lng -> sview-20_08.tar.gz/StImageViewer/lang/czech/StImageViewer.lng
Changed
55
1
2
?1252=Heal anamorphic 1080p/720p
3
1260=Sousední
4
1261=Lineární
5
+?1263=Trilinear
6
1270=Resetovat nastavení
7
1271=Jas
8
1272=Sytost
9
10
1281=Koule
11
1282=Válec
12
?1283=Cubemap
13
+?1284=Hemisphere
14
?1285=Track orientation
15
?1286=Track orientation (poor)
16
?1288=Stick at panorama 360°
17
?1291=Cubemap 6x1 - flip Z
18
?1292=Cubemap 3x2 - flip Z
19
+?1293=Equiangular cubemap
20
+?1294=Theater
21
1400=Zobrazovací zařizení
22
1401=O modulu
23
1402=Zobrazovat snímkování (fps)
24
1403=Vertikální synchronizace
25
+?1404=Exclusive Fullscreen mode
26
1500=Nápověda
27
1501=O aplikaci sView…
28
1502=Aktualizace
29
30
?1705=On one click windowed mode
31
?1710=Hide system navigation bar
32
?1711=Open last viewed file on startup
33
+?1712=Swap JPS/PNS views order
34
2000=Otevřít
35
2001=Otevřít LEVÝ
36
2002=Otevřít PRAVÝ
37
38
5004=Načítání
39
5005=ms
40
5006=Poměr stran pixelu
41
-5007=Barevný model
42
+5007=Formát pixelu
43
5008=(metada nejsou v informaci obsažena)
44
5009=(neobsahuje metadata)
45
5011=(informace není obsažena v metadatech,\nale byla přidělena podle jména souboru)
46
+5012=Barevný model
47
5100=JPEG komentář
48
5101=JPS komentář
49
5200=Výrobce kamery
50
51
?6040=X Rotation - up
52
?6041=X Rotation - down
53
?6042=Enable/disable panorama mode
54
+?6043=Show/hide GUI
55
sview-17_04.tar.gz/StImageViewer/lang/english/StImageViewer.lng -> sview-20_08.tar.gz/StImageViewer/lang/english/StImageViewer.lng
Changed
55
1
2
1252=Heal anamorphic 1080p/720p
3
1260=Nearest
4
1261=Linear
5
+1263=Trilinear
6
1270=Reset to defaults
7
1271=Brightness
8
1272=Saturation
9
10
1281=Sphere
11
1282=Cylinder
12
1283=Cubemap
13
+1284=Hemisphere
14
1285=Track orientation
15
1286=Track orientation (poor)
16
1288=Stick at panorama 360°
17
1291=Cubemap 6x1 - flip Z
18
1292=Cubemap 3x2 - flip Z
19
+1293=Equiangular cubemap
20
+1294=Theater
21
1400=Change device
22
1401=About Plugin...
23
1402=Show FPS
24
1403=VSync
25
+1404=Exclusive Fullscreen mode
26
1500=Help
27
1501=About...
28
1502=Check for updates
29
30
1705=On one click windowed mode
31
1710=Hide system navigation bar
32
1711=Open last viewed file on startup
33
+1712=Swap JPS/PNS views order
34
2000=Choose the image file to open
35
2001=Choose LEFT image file to open
36
2002=Choose RIGHT image file to open
37
38
5004=Load time
39
5005=ms
40
5006=Pixel ratio
41
-5007=Color model
42
+5007=Pixel format
43
5008=(does not stored in metadata)
44
5009=(does not match metadata)
45
5011=(does not stored in metadata,\nbut detected from file name)
46
+5012=Color model
47
5100=JPEG Comment
48
5101=JPS Comment
49
5200=Camera Maker
50
51
6040=X Rotation - up
52
6041=X Rotation - down
53
6042=Enable/disable panorama mode
54
+6043=Show/hide GUI
55
sview-17_04.tar.gz/StImageViewer/lang/french/StImageViewer.lng -> sview-20_08.tar.gz/StImageViewer/lang/french/StImageViewer.lng
Changed
55
1
2
?1252=Heal anamorphic 1080p/720p
3
1260=Plus proche
4
1261=Lineaire
5
+1263=Trilinéaire
6
1270=Rétablir par défaut
7
1271=Brightness
8
1272=Saturation
9
10
1281=Sphère
11
1282=Cylindre
12
1283=Cubemap
13
+1284=Hémisphère
14
?1285=Track orientation
15
?1286=Track orientation (poor)
16
?1288=Stick at panorama 360°
17
?1291=Cubemap 6x1 - flip Z
18
?1292=Cubemap 3x2 - flip Z
19
+?1293=Equiangular cubemap
20
+1294=Théâtre
21
1400=Changer la sortie
22
1401=A propos du Plugin...
23
1402=Voir I/S
24
1403=Synchro Vert.
25
+?1404=Exclusive Fullscreen mode
26
1500=Aide
27
1501=A Propos...
28
1502=Vérifier nouvelle version
29
30
?1705=On one click windowed mode
31
?1710=Hide system navigation bar
32
?1711=Open last viewed file on startup
33
+1712=JPS/PNS échange de vues pour
34
2000=Choix du fichier image à ouvrir
35
2001=Choix du fichier image Gauche à ouvrir
36
2002=Choix du fichier image Droite à ouvrir
37
38
5004=Temps de démarrage
39
5005=ms
40
5006=Pixel ratio
41
-5007=Modèle colorimétrique
42
+5007=Pixel format
43
?5008=(does not stored in metadata)
44
?5009=(does not match metadata)
45
?5011=(does not stored in metadata,\nbut detected from file name)
46
+5012=Modèle colorimétrique
47
5100=JPEG commentaire
48
5101=JPS commentaire
49
5200=Camera Maker
50
51
?6040=X Rotation - up
52
?6041=X Rotation - down
53
6042=Activer / désactiver le mode panorama
54
+6043=Masquer l'interface
55
sview-17_04.tar.gz/StImageViewer/lang/german/StImageViewer.lng -> sview-20_08.tar.gz/StImageViewer/lang/german/StImageViewer.lng
Changed
55
1
2
?1252=Heal anamorphic 1080p/720p
3
1260=Nearest
4
1261=Linear
5
+1263=Trilinear
6
1270=Auf Standardwerte zurücksetzen
7
1271=Helligkeit
8
1272=Sättigung
9
10
1281=Kugel
11
1282=Zylinder
12
1283=Cubemap
13
+1284=Hemisphäre
14
?1285=Track orientation
15
?1286=Track orientation (poor)
16
?1288=Stick at panorama 360°
17
?1291=Cubemap 6x1 - flip Z
18
?1292=Cubemap 3x2 - flip Z
19
+?1293=Equiangular cubemap
20
+1294=Theater
21
1400=Gerät ändern
22
1401=Über Plugin...
23
1402=FPS anzeigen
24
1403=VSync
25
+1404=Exklusiver Vollbildmodus
26
1500=Hilfe
27
1501=Über...
28
1502=Nach Updates suchen
29
30
?1705=Only when windowed
31
1710=Navigationsleiste ausblenden
32
?1711=Open last viewed file on startup
33
+1712=JPS/PNS-Ansichten, um zu tauschen
34
2000=Wählen die Bilddatei zu öffnen
35
2001=Wählen die linke Bilddatei zu öffnen
36
2002=Wählen die rechte Bilddatei zu öffnen
37
38
5004=Ladezeit
39
5005=ms
40
5006=Pixelseitenverhältnis
41
-5007=Farbmodell
42
+5007=Pixel format
43
5008=(nicht in Metadaten gespeichert)
44
5009=(keine Metadaten übereinstimmen)
45
5011=(nicht in Metadaten gespeichert,\nsondern von Dateinamen detektiert)
46
+5012=Farbmodell
47
5100=JPEG Kommentar
48
5101=JPS Kommentar
49
5200=Kamerahersteller
50
51
6040=X-Drehung - nach oben
52
6041=X-Drehung - nach unten
53
6042=Aktivieren / Deaktivieren der Panorama-Modus
54
+6043=GUI ausblenden
55
sview-17_04.tar.gz/StImageViewer/lang/korean/StImageViewer.lng -> sview-20_08.tar.gz/StImageViewer/lang/korean/StImageViewer.lng
Changed
55
1
2
?1252=Heal anamorphic 1080p/720p
3
?1260=Nearest
4
?1261=Linear
5
+?1263=Trilinear
6
1270=기본값으로 리셋
7
1271=밝기
8
?1272=Saturation
9
10
?1281=Sphere
11
?1282=Cylinder
12
?1283=Cubemap
13
+?1284=Hemisphere
14
?1285=Track orientation
15
?1286=Track orientation (poor)
16
?1288=Stick at panorama 360°
17
?1291=Cubemap 6x1 - flip Z
18
?1292=Cubemap 3x2 - flip Z
19
+?1293=Equiangular cubemap
20
+?1294=Theater
21
1400=장치 변경
22
?1401=About Plugin...
23
?1402=Show FPS
24
?1403=VSync
25
+?1404=Exclusive Fullscreen mode
26
1500=도움말
27
1501=이 프로그램에 대해...
28
1502=업데이트 확인
29
30
?1705=On one click windowed mode
31
?1710=Hide system navigation bar
32
?1711=Open last viewed file on startup
33
+?1712=Swap JPS/PNS views order
34
2000=열어볼 이미지 파일 선택
35
2001=왼쪽 이미지 선택
36
2002=오른쪽 이미지 선택
37
38
?5004=Load time
39
?5005=ms
40
?5006=Pixel ratio
41
-?5007=Color model
42
+?5007=Pixel format
43
?5008=(does not stored in metadata)
44
?5009=(does not match metadata)
45
?5011=(does not stored in metadata,\nbut detected from file name)
46
+?5012=Color model
47
?5100=JPEG Comment
48
?5101=JPS Comment
49
?5200=Camera Maker
50
51
?6040=X Rotation - up
52
?6041=X Rotation - down
53
?6042=Enable/disable panorama mode
54
+?6043=Show/hide GUI
55
sview-17_04.tar.gz/StImageViewer/lang/russian/StImageViewer.lng -> sview-20_08.tar.gz/StImageViewer/lang/russian/StImageViewer.lng
Changed
59
1
2
1250=Исходное
3
1251=Запомнить
4
?1252=Heal anamorphic 1080p/720p
5
-1260=Nearest
6
-1261=Linear
7
+1260=Без сглаживания
8
+1261=Линейное
9
+1263=Трилинейное
10
1270=Сбросить настройки
11
1271=Яркость
12
1272=Насыщенность
13
14
1281=Сфера
15
1282=Цилиндр
16
1283=Куб
17
+1284=Полусфера
18
1285=Отслеживать ориентацию
19
1286=Отслеживать ориентацию (poor)
20
1288=Закрепить панорамный режим 360°
21
1291=Кубмапа 6x1 - инвертировать Z
22
1292=Кубмапа 3x2 - инвертировать Z
23
+?1293=Equiangular cubemap
24
+1294=Киноэкран
25
1400=Выбрать устройство
26
1401=О модуле...
27
1402=Отображать FPS
28
1403=Верт. синхронизация
29
+1404=Эксклюзивный полноэкранный режим
30
1500=Помощь
31
1501=О программе...
32
1502=Проверить обновления
33
34
1705=Только в оконном режиме
35
1710=Скрыть панель навигации
36
1711=Открывать последний файл при старте
37
+1712=Поменять ракурсы местами в JPS/PNS
38
2000=Выберите картинку
39
2001=Выберите файл с ЛЕВЫМ ракурсом
40
2002=Выберите файл с ПРАВЫМ ракурсом
41
42
5004=Время загрузки
43
5005=мс
44
5006=Пропорции пикселя
45
-5007=Color model
46
+5007=Пиксельный формат
47
5008=(информация отсутствует в метаданных)
48
5009=(не соответствует метаданным)
49
5011=(информация отсутствует в метаданных,\nно была определена по имени файла)
50
+5012=Color model
51
5100=JPEG комментарий
52
5101=JPS комментарий
53
5200=Производитель камеры
54
55
6040=X наклон - наверх
56
6041=X наклон - вниз
57
6042=Включить/выключить панорамный режим
58
+6043=Скрыть интерфейс
59
sview-20_08.tar.gz/StImageViewer/lang/spanish
Added
2
1
+(directory)
2
sview-20_08.tar.gz/StImageViewer/lang/spanish/StImageViewer.lng
Added
188
1
2
+# Spanish translation file for StImageViewer
3
+--------
4
+1000=Anterior imagen
5
+1001=Siguiente imagen
6
+1002=Cambiar izquierdo/derecho
7
+1003=Revertir cambio izquierdo/derecho
8
+1004=Formato estereoscópico:
9
+1015=Abrir otra imagen
10
+1028=Mostrar/Ocultar lista de reproducción
11
+1029=Cambiar entre\npantalla completa/ventana
12
+1100=Medios
13
+1101=Abrir imagen...
14
+1102=Guardar imagen como...
15
+1103=Formato estereoscópico
16
+1104=Información de la imagen
17
+1109=Salir
18
+1110=Desde un archivo
19
+1111=Archivos izquierdo+derecho
20
+1130=Fuente
21
+1131=Mono
22
+1132=Vista cruzada
23
+1133=Par paralelo
24
+1134=Sobre/bajo (D/I)
25
+1135=Sobre/bajo (I/D)
26
+1136=Entrelazado
27
+1137=Anaglifo rojo/cian
28
+1138=Anaglifo verde/rojo+azul
29
+1139=Anaglifo amarillo/azul
30
+1142=2 canales
31
+1200=Ver
32
+1201=Salida estéreo
33
+1202=Pantalla completa
34
+1203=Restablecer
35
+1204=Cambiar izquierdo/derecho
36
+1205=Relación de visualización
37
+1206=Filtro más suave
38
+1207=Ajustar imagen
39
+1208=Panorámica
40
+1210=Estéreo
41
+1211=Vista izquierda
42
+1212=Vista derecha
43
+1213=Par paralelo
44
+1214=Vista cruzada
45
+1250=Fuente
46
+1251=Conservar al reiniciar
47
+1252=Corregir anamórfico 1080p/720p
48
+1260=Más cercano
49
+1261=Lineal
50
+1263=Trilineal
51
+1270=Restablecer predeterminados
52
+1271=Brillo
53
+1272=Saturación
54
+1273=Gamma
55
+1280=Desactivado
56
+1281=Esfera
57
+1282=Cilindro
58
+1283=Cubemap
59
+1284=Hemisferio
60
+1285=Orientación de pista
61
+1286=Orientación de pista (deficiente)
62
+1288=Mantener en panorámica de 360°
63
+1291=Cubemap 6x1 - voltear Z
64
+1292=Cubemap 3x2 - voltear Z
65
+?1293=Equiangular cubemap
66
+1294=Teatro
67
+1400=Cambiar dispositivo
68
+1401=Acerca del complemento...
69
+1402=Mostrar FPS
70
+1403=Sincronización vertical
71
+1404=Modo de pantalla completa exclusiva
72
+1500=Ayuda
73
+1501=Acerca de...
74
+1502=Buscar actualizaciones
75
+1503=Texto de la licencia
76
+1504=Idioma (Language)
77
+1506=Consejos para el usuario
78
+1508=Acerca del sistema
79
+1509=Escala de la interfaz
80
+1510=Teclas de acceso rápido
81
+1511=Ajustes
82
+1520=Ahora
83
+1521=Cada día
84
+1522=Cada semana
85
+1523=Cada año
86
+1524=Nunca
87
+1590=Pequeño
88
+1591=Normal
89
+1592=Grande
90
+1593=Forzar HiDPI 2X
91
+1701=Salir de sView con escape
92
+1702=No salir
93
+1703=Con un clic
94
+1704=Con doble clic
95
+1705=Modo de ventana con un clic
96
+1710=Ocultar la barra de navegación del sistema
97
+1711=Abrir el último archivo visto al iniciar
98
+1712=JPS/PNS ve intercambio orden
99
+2000=Elije el archivo de imagen para abrir
100
+2001=Elige el archivo de la imagen IZQUIERDA para abrir
101
+2002=Elije el archivo de la imagen DERECHA para abrir
102
+2003=Información de la imagen
103
+2004=No hay disponible información
104
+2005=Eliminación de archivo
105
+2006=¿Realmente deseas eliminar completamente este archivo?
106
+2007=Guardando metadatos del archivo
107
+2008=¿Realmente deseas guardar los metadatos al archivo?
108
+2009=Los metadatos solo se pueden guardar en archivos JPEG.
109
+2010=Elije la ubicación para guardar la instantánea
110
+2011=¡Nada para guardar!
111
+2012=¡Instantánea no disponible!
112
+2013=Asignar nueva tecla de acceso rápido para la acción\n<i>{0}</i>
113
+2014=En conflicto con: <i>{0}</i>
114
+3000=sView - Visor de imágenes
115
+3001=versión
116
+3002=El visor de imágenes te permite abrir imágenes estereoscópicas en formatos JPEG, PNG, MPO y muchos más.\n © {0} Kirill Gavrilov <{1}>\nSitio oficial: {2}\n\nEste programa se distribuye bajo licencia GPL 3.0
117
+3003=Hay disponible una nueva versión de sView en el sitio oficial: www.sview.ru.\nPor favor, actualiza el programa.
118
+3004=Información del sistema
119
+4000=Cerrar
120
+4001=Cancelar
121
+4006=Guardar
122
+4007=Eliminar
123
+4008=Predeterminado
124
+4009=Predeterminados
125
+4010=Asignar
126
+5000=[izquierdo]
127
+5001=[derecho]
128
+5002=Nombre de archivo
129
+5003=Dimensiones
130
+5004=Tiempo de carga
131
+5005=ms
132
+5006=Relación de pixeles
133
+5007=Formato de píxel
134
+5008=(no almacenado en los metadatos)
135
+5009=(no coincide con los metadatos)
136
+5011=(no almacenado en los metadatos,\npero detectado en el nombre de archivo)
137
+5012=Modelo de color
138
+5100=Comentario JPEG
139
+5101=Comentario JPS
140
+5200=Marca de la cámara
141
+5201=Modelo de la cámara
142
+5202=Comentario del usuario
143
+5203=Marca de tiempo de la imagen
144
+6000=Cambiar entre pantalla completa/ventana
145
+6001=Mostrar/ocultar medidor de FPS
146
+6002=Formato estéreo: Automático
147
+6003=Formato estéreo: Mono
148
+6004=Formato estéreo: Sobre/bajo
149
+6005=Formato estéreo: En paralelo
150
+6006=Mostrar información del archivo
151
+6007=Lista de reproducción: Ir al primer elemento
152
+6008=Lista de reproducción: Ir al último elemento
153
+6009=Lista de reproducción: Ir al anterior elemento
154
+6010=Lista de reproducción: Ir al siguiente elemento
155
+6011=Lista de reproducción: Iniciar/Detener presentación
156
+6012=Guardar en formato PNG
157
+6013=Guardar en formato JPEG
158
+6014=Guardar metadatos del archivo
159
+6015=Eliminar el archivo del sistema de archivos
160
+6016=Restablecer el ajuste de la imagen
161
+6017=Restablecer la posición de la imagen
162
+6018=Cambiar izquierdo/derecho
163
+6019=Corrección gamma: disminuir
164
+6020=Corrección gamma: aumentar
165
+6021=Separación DX: disminuir
166
+6022=Separación DX: aumentar
167
+6023=Separación DY: disminuir
168
+6024=Separación DY: aumentar
169
+6025=Separación angular: disminuir
170
+6026=Separación angular: aumentar
171
+6027=Rotar 90° a la izquierda
172
+6028=Rotar 90° a la derecha
173
+6029=Rotar a la izquierda
174
+6030=Rotar a la derecha
175
+6031=Seleccionar el siguiente modo de visualización
176
+6032=Barrido: navegar hacia la izquierda
177
+6033=Barrido: navegar hacia la derecha
178
+6034=Barrido: navegar hacia arriba
179
+6035=Barrido: navegar hacia abajo
180
+6036=Escala: aumentar
181
+6037=Escala: reducir
182
+6038=Rotación Y: izquierda
183
+6039=Rotación Y: derecha
184
+6040=Rotación X: arriba
185
+6041=Rotación X: abajo
186
+6042=Activar/Desactivar modo panorámico
187
+6043=Mostrar/ocultar GUI
188
sview-17_04.tar.gz/StMoviePlayer/StMovieOpenDialog.cpp -> sview-20_08.tar.gz/StMoviePlayer/StMovieOpenDialog.cpp
Changed
111
1
2
}
3
4
void StMovieOpenDialog::setPaths(const StString& thePathLeft,
5
- const StString& thePathRight) {
6
+ const StString& thePathRight,
7
+ const StMovieOpenDialog::DialogState theMode) {
8
StMutexAuto aLock(myMutex);
9
if(myState != StMovieOpenDialog::Dialog_Inactive) {
10
return;
11
}
12
13
- myPathVideoL = thePathLeft;
14
- myPathVideoR = thePathRight;
15
+ myPathVideoL.clear();
16
+ myPathVideoR.clear();
17
myPathAudio.clear();
18
myPathSubs .clear();
19
- if(!myPathVideoL.isEmpty()) {
20
- myState = StMovieOpenDialog::Dialog_HasFiles;
21
+ switch(theMode) {
22
+ case Dialog_Audio: {
23
+ myPathAudio = thePathLeft;
24
+ if(!myPathAudio.isEmpty()) {
25
+ myState = StMovieOpenDialog::Dialog_HasFiles;
26
+ }
27
+ break;
28
+ }
29
+ case Dialog_Subtitles: {
30
+ myPathSubs = thePathLeft;
31
+ if(!myPathSubs.isEmpty()) {
32
+ myState = StMovieOpenDialog::Dialog_HasFiles;
33
+ }
34
+ break;
35
+ }
36
+ case Dialog_SingleMovie:
37
+ case Dialog_DoubleMovie:
38
+ default: {
39
+ myPathVideoL = thePathLeft;
40
+ myPathVideoR = thePathRight;
41
+ if(!myPathVideoL.isEmpty()) {
42
+ myState = StMovieOpenDialog::Dialog_HasFiles;
43
+ }
44
+ break;
45
+ }
46
}
47
}
48
49
50
myPathAudio .clear();
51
myPathSubs .clear();
52
53
- StString aTitle;
54
- const StMIMEList* aMimeList = &myPlugin->myVideo->getMimeListVideo();
55
+ StOpenFileName anOpenInfo;
56
+ anOpenInfo.Folder = myFolder;
57
switch(myState) {
58
case Dialog_DoubleMovie:
59
- aTitle = myPlugin->tr(StMoviePlayerStrings::DIALOG_OPEN_LEFT);
60
+ anOpenInfo.Title = myPlugin->tr(StMoviePlayerStrings::DIALOG_OPEN_LEFT);
61
+ anOpenInfo.Filter = myPlugin->myVideo->getMimeListVideo();
62
+ anOpenInfo.FilterTitle = "Video Files";
63
break;
64
case Dialog_Audio:
65
- aTitle = "Choose audio file to attach";
66
- aMimeList = &myPlugin->myVideo->getMimeListAudio();
67
+ anOpenInfo.Title = myPlugin->tr(StMoviePlayerStrings::DIALOG_OPEN_AUDIO);
68
+ anOpenInfo.Filter = myPlugin->myVideo->getMimeListAudio();
69
+ anOpenInfo.FilterTitle = "Audio Files";
70
break;
71
case Dialog_Subtitles:
72
- aTitle = "Choose subtitles file to attach";
73
- aMimeList = &myPlugin->myVideo->getMimeListSubtitles();
74
+ anOpenInfo.Title = myPlugin->tr(StMoviePlayerStrings::DIALOG_OPEN_SUBTITLES);
75
+ anOpenInfo.Filter = myPlugin->myVideo->getMimeListSubtitles();
76
+ anOpenInfo.FilterTitle = "Subtitle Files";
77
break;
78
case Dialog_SingleMovie:
79
default:
80
- aTitle = myPlugin->tr(StMoviePlayerStrings::DIALOG_OPEN_FILE);
81
+ anOpenInfo.Title = myPlugin->tr(StMoviePlayerStrings::DIALOG_OPEN_FILE);
82
+ anOpenInfo.Filter = myPlugin->myVideo->getMimeListVideo();
83
+ anOpenInfo.FilterTitle = "Video Files";
84
+ anOpenInfo.ExtraFilter = myPlugin->myVideo->getMimeListImages();
85
+ anOpenInfo.ExtraFilterTitle = "Image files";
86
break;
87
}
88
89
- StString aFilePath, aDummy;
90
- if(!StFileNode::openFileDialog(myFolder, aTitle, *aMimeList, aFilePath, false)) {
91
+ StString aFilePath;
92
+ if(!StFileNode::openFileDialog(aFilePath, anOpenInfo, false)) {
93
StMutexAuto aLock(myMutex);
94
myState = StMovieOpenDialog::Dialog_Inactive;
95
return;
96
97
98
switch(myState) {
99
case Dialog_DoubleMovie: {
100
- aTitle = myPlugin->tr(StMoviePlayerStrings::DIALOG_OPEN_RIGHT);
101
+ anOpenInfo.Title = myPlugin->tr(StMoviePlayerStrings::DIALOG_OPEN_RIGHT);
102
+ StString aDummy;
103
StFileNode::getFolderAndFile(aFilePath, myFolder, aDummy);
104
+ anOpenInfo.Folder = myFolder;
105
myPathVideoL = aFilePath;
106
- if(!StFileNode::openFileDialog(myFolder, aTitle, *aMimeList, myPathVideoR, false)) {
107
+ if(!StFileNode::openFileDialog(myPathVideoR, anOpenInfo, false)) {
108
StMutexAuto aLock(myMutex);
109
myState = StMovieOpenDialog::Dialog_Inactive;
110
return;
111
sview-17_04.tar.gz/StMoviePlayer/StMovieOpenDialog.h -> sview-20_08.tar.gz/StMoviePlayer/StMovieOpenDialog.h
Changed
11
1
2
* Set paths to open.
3
*/
4
ST_LOCAL void setPaths(const StString& thePathLeft,
5
- const StString& thePathRight);
6
+ const StString& thePathRight,
7
+ const StMovieOpenDialog::DialogState theMode);
8
9
private:
10
11
sview-17_04.tar.gz/StMoviePlayer/StMoviePlayer.cpp -> sview-20_08.tar.gz/StMoviePlayer/StMoviePlayer.cpp
Changed
709
1
2
/**
3
- * Copyright © 2007-2017 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2007-2020 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* StMoviePlayer program is free software: you can redistribute it and/or modify
7
* it under the terms of the GNU General Public License as published by
8
9
static const char ST_ARGUMENT_FILE_DEMO[] = "demo";
10
static const char ST_ARGUMENT_FILE_PAUSE[] = "pause";
11
static const char ST_ARGUMENT_FILE_PAUSED[]= "paused";
12
+ static const char ST_ARGUMENT_FILE_SEEK[] = "seek";
13
static const char ST_ARGUMENT_MONITOR[] = "monitorId";
14
static const char ST_ARGUMENT_WINLEFT[] = "windowLeft";
15
static const char ST_ARGUMENT_WINTOP[] = "windowTop";
16
17
void StMoviePlayer::doPause(const StPauseEvent& theEvent) {
18
StApplication::doPause(theEvent);
19
saveAllParams();
20
- if(!myVideo.isNull()) {
21
+ if(myVideo.isNull()) {
22
+ return;
23
+ }
24
+
25
+ // pause video but keep playing audio in background
26
+ StWinAttr anAttribs[] = {
27
+ StWinAttr_ToBlockSleepSystem, (StWinAttr )0,
28
+ StWinAttr_ToBlockSleepDisplay, (StWinAttr )0,
29
+ StWinAttr_NULL
30
+ };
31
+ myWindow->getAttributes(anAttribs);
32
+ if(anAttribs[1] == (StWinAttr )0
33
+ || anAttribs[3] != (StWinAttr )0) {
34
myVideo->pushPlayEvent(ST_PLAYEVENT_PAUSE);
35
}
36
}
37
38
params.SubtitlesParser->setName(tr(MENU_SUBTITLES_PARSER));
39
params.SubtitlesParser->defineOption(0, tr(MENU_SUBTITLES_PLAIN_TEXT));
40
params.SubtitlesParser->defineOption(1, tr(MENU_SUBTITLES_LITE_HTML));
41
+ params.SubtitlesApplyStereo->setName(tr(MENU_SUBTITLES_STEREO));
42
params.AudioAlHrtf->setName(stCString("Audio HRTF mixing"));
43
params.AudioAlHrtf->defineOption(0, stCString("Auto"));
44
params.AudioAlHrtf->defineOption(1, stCString("Forced ON"));
45
46
params.SrcStereoFormat->setName(tr(MENU_MEDIA_SRC_FORMAT));
47
params.ToShowPlayList->setName(tr(VIDEO_LIST));
48
params.ToShowAdjustImage->setName(tr(MENU_VIEW_IMAGE_ADJUST));
49
+ params.ToSwapJPS->setName(tr(OPTION_SWAP_JPS));
50
params.ToStickPanorama->setName(tr(MENU_VIEW_STICK_PANORAMA360));
51
params.ToTrackHead->setName(tr(MENU_VIEW_TRACK_HEAD));
52
params.ToTrackHeadAudio->setName(tr(MENU_VIEW_TRACK_HEAD_AUDIO));
53
54
params.ToShowFps->setName(tr(MENU_FPS_METER));
55
params.ToShowMenu->setName(stCString("Show main menu"));
56
params.ToShowTopbar->setName(stCString("Show top toolbar"));
57
+ params.ToShowBottom->setName(stCString("Show seekbar"));
58
+ params.ToMixImagesVideos->setName(stCString("Mix images & videos"));
59
+ params.SlideShowDelay->setName(stCString("Slideshow delay"));
60
params.IsMobileUI->setName(stCString("Mobile UI"));
61
+ params.IsExclusiveFullScreen->setName(tr(MENU_EXCLUSIVE_FULLSCREEN));
62
params.IsVSyncOn->setName(tr(MENU_FPS_VSYNC));
63
params.ToLimitFps->setName(tr(MENU_FPS_BOUND));
64
+ params.ToSmoothUploads->setName("Smooth texture uploading");
65
params.StartWebUI->setName(stCString("Web UI start option"));
66
params.StartWebUI->defineOption(WEBUI_OFF, tr(MENU_MEDIA_WEBUI_OFF));
67
params.StartWebUI->defineOption(WEBUI_ONCE, tr(MENU_MEDIA_WEBUI_ONCE));
68
69
#if defined(_WIN32)
70
const StCString aGpuAcc = stCString(" (DXVA2)");
71
#elif defined(__APPLE__)
72
- const StCString aGpuAcc = stCString(" (VDA)");
73
+ const StCString aGpuAcc = stCString(" (VideoToolbox)");
74
#elif defined(__ANDROID__)
75
const StCString aGpuAcc = stCString(""); //stCString(" (Android Media Codec)");
76
#else
77
78
params.SubtitlesParallax->setTolerance(0.1f);
79
params.ToSearchSubs = new StBoolParamNamed(true, stCString("toSearchSubs"));
80
params.SubtitlesParser = new StEnumParam(1, stCString("subsParser"));
81
+ params.SubtitlesApplyStereo = new StBoolParamNamed(true, stCString("subsApplyStereo"));
82
params.AudioAlDevice = new StALDeviceParam();
83
params.AudioAlHrtf = new StEnumParam(0, stCString("alHrtfRequest"));
84
params.AudioGain = new StFloat32Param( 0.0f, // sound is unattenuated
85
86
params.ToShowPlayList->signals.onChanged = stSlot(this, &StMoviePlayer::doShowPlayList);
87
params.ToShowAdjustImage = new StBoolParamNamed(false, stCString("showAdjustImage"));
88
params.ToShowAdjustImage->signals.onChanged = stSlot(this, &StMoviePlayer::doShowAdjustImage);
89
+ params.ToSwapJPS = new StBoolParamNamed(false, stCString("toSwapJPS"));
90
+ params.ToSwapJPS->signals.onChanged = stSlot(this, &StMoviePlayer::doChangeSwapJPS);
91
params.ToStickPanorama = new StBoolParamNamed(false, stCString("toStickPano360"));
92
params.ToStickPanorama->signals.onChanged = stSlot(this, &StMoviePlayer::doChangeStickPano360);
93
params.ToTrackHead = new StBoolParamNamed(true, stCString("toTrackHead"));
94
95
params.ToShowFps = new StBoolParamNamed(false, stCString("toShowFps"));
96
params.ToShowMenu = new StBoolParamNamed(true, stCString("toShowMenu"));
97
params.ToShowTopbar= new StBoolParamNamed(true, stCString("toShowTopbar"));
98
+ params.ToShowBottom= new StBoolParamNamed(true, stCString("toShowBottom"));
99
+ params.ToMixImagesVideos = new StBoolParamNamed(false, stCString("toMixImagesVideos"));
100
+ params.ToMixImagesVideos->signals.onChanged = stSlot(this, &StMoviePlayer::doChangeMixImagesVideos);
101
+ params.SlideShowDelay = new StFloat32Param(4.0f, stCString("slideShowDelay2"));
102
+ params.SlideShowDelay->setMinMaxValues(1.0f, 10.0f);
103
+ params.SlideShowDelay->setDefValue(4.0f);
104
+ params.SlideShowDelay->setStep(1.0f);
105
+ params.SlideShowDelay->setTolerance(0.1f);
106
+ params.SlideShowDelay->setFormat(stCString("%01.1f s"));
107
params.IsMobileUI = new StBoolParamNamed(StWindow::isMobile(), stCString("isMobileUI"));
108
params.IsMobileUI->signals.onChanged = stSlot(this, &StMoviePlayer::doChangeMobileUI);
109
params.IsMobileUISwitch = new StBoolParam(params.IsMobileUI->getValue());
110
params.IsMobileUISwitch->signals.onChanged = stSlot(this, &StMoviePlayer::doScaleHiDPI);
111
+ params.IsExclusiveFullScreen = new StBoolParamNamed(false, stCString("isExclusiveFullScreen"));
112
params.IsVSyncOn = new StBoolParamNamed(true, stCString("vsync"));
113
params.IsVSyncOn->signals.onChanged = stSlot(this, &StMoviePlayer::doSwitchVSync);
114
StApplication::params.VSyncMode->setValue(StGLContext::VSync_ON);
115
params.ToLimitFps = new StBoolParamNamed(true, stCString("toLimitFps"));
116
+ params.ToSmoothUploads = new StBoolParamNamed(true, stCString("toSmoothUploads"));
117
params.StartWebUI = new StEnumParam(WEBUI_OFF, stCString("webuiOn"));
118
params.ToPrintWebErrors = new StBoolParamNamed(true, stCString("webuiShowErrors"));
119
params.IsLocalWebUI = new StBoolParamNamed(false, stCString("isLocalWebUI"));
120
121
mySettings->loadParam (params.SubtitlesSize);
122
mySettings->loadParam (params.SubtitlesParallax);
123
mySettings->loadParam (params.SubtitlesParser);
124
+ mySettings->loadParam (params.SubtitlesApplyStereo);
125
mySettings->loadParam (params.ToSearchSubs);
126
127
myToCheckPoorOrient = !mySettings->loadParam(params.ToTrackHead);
128
+ mySettings->loadParam (params.ToSwapJPS);
129
mySettings->loadParam (params.ToStickPanorama);
130
mySettings->loadParam (params.ToTrackHeadAudio);
131
mySettings->loadParam (params.ToForceBFormat);
132
mySettings->loadParam (params.AudioAlHrtf);
133
mySettings->loadParam (params.ToShowFps);
134
+ mySettings->loadParam (params.SlideShowDelay);
135
+ mySettings->loadParam (params.ToMixImagesVideos);
136
mySettings->loadParam (params.IsMobileUI);
137
+ mySettings->loadParam (params.IsExclusiveFullScreen);
138
mySettings->loadParam (params.IsVSyncOn);
139
mySettings->loadParam (params.ToLimitFps);
140
+ mySettings->loadParam (params.ToSmoothUploads);
141
mySettings->loadParam (params.UseGpu);
142
mySettings->loadParam (params.UseOpenJpeg);
143
144
145
anAction = new StActionBool(stCString("DoShowFPS"), params.ToShowFps);
146
addAction(Action_ShowFps, anAction, ST_VK_F12);
147
148
+ anAction = new StActionIntSlot(stCString("DoShowGUI"), stSlot(this, &StMoviePlayer::doShowHideGUI), 0);
149
+ addAction(Action_ShowGUI, anAction, ST_VK_TILDE);
150
+
151
anAction = new StActionIntValue(stCString("DoSrcAuto"), params.SrcStereoFormat, StFormat_AUTO);
152
addAction(Action_SrcAuto, anAction, ST_VK_A);
153
154
155
156
anAction = new StActionIntSlot(stCString("DoPanoramaOnOff"), stSlot(this, &StMoviePlayer::doPanoramaOnOff), 0);
157
addAction(Action_PanoramaOnOff, anAction, ST_VK_P);
158
+
159
+ {
160
+ anAction = new StActionIntSlot(stCString("DoOutStereoNormal"), stSlot(this, &StMoviePlayer::doSetStereoOutput), StGLImageRegion::MODE_STEREO);
161
+ addAction(Action_OutStereoNormal, anAction);
162
+
163
+ anAction = new StActionIntSlot(stCString("DoOutStereoLeftView"), stSlot(this, &StMoviePlayer::doSetStereoOutput), StGLImageRegion::MODE_ONLY_LEFT);
164
+ addAction(Action_OutStereoLeftView, anAction);
165
+
166
+ anAction = new StActionIntSlot(stCString("DoOutStereoRightView"), stSlot(this, &StMoviePlayer::doSetStereoOutput), StGLImageRegion::MODE_ONLY_RIGHT);
167
+ addAction(Action_OutStereoRightView, anAction);
168
+
169
+ anAction = new StActionIntSlot(stCString("DoOutStereoParallelPair"), stSlot(this, &StMoviePlayer::doSetStereoOutput), StGLImageRegion::MODE_PARALLEL);
170
+ addAction(Action_OutStereoParallelPair, anAction);
171
+
172
+ anAction = new StActionIntSlot(stCString("DoOutStereoCrossEyed"), stSlot(this, &StMoviePlayer::doSetStereoOutput), StGLImageRegion::MODE_CROSSYED);
173
+ addAction(Action_OutStereoCrossEyed, anAction);
174
+ }
175
}
176
177
bool StMoviePlayer::resetDevice() {
178
179
mySettings->saveParam (params.SubtitlesSize);
180
mySettings->saveParam (params.SubtitlesParallax);
181
mySettings->saveParam (params.SubtitlesParser);
182
+ mySettings->saveParam (params.SubtitlesApplyStereo);
183
mySettings->saveParam (params.ToSearchSubs);
184
mySettings->saveParam (params.TargetFps);
185
mySettings->saveString(params.AudioAlDevice->getKey(), params.AudioAlDevice->getUtfTitle());
186
187
mySettings->saveParam (params.ToShowPlayList);
188
mySettings->saveParam (params.ToShowAdjustImage);
189
190
+ mySettings->saveParam (params.ToSwapJPS);
191
mySettings->saveParam (params.ToStickPanorama);
192
mySettings->saveParam (params.ToTrackHead);
193
mySettings->saveParam (params.ToTrackHeadAudio);
194
mySettings->saveParam (params.ToForceBFormat);
195
mySettings->saveParam (params.ToShowFps);
196
+ mySettings->saveParam (params.SlideShowDelay);
197
+ mySettings->saveParam (params.ToMixImagesVideos);
198
mySettings->saveParam (params.IsMobileUI);
199
+ mySettings->saveParam (params.IsExclusiveFullScreen);
200
mySettings->saveParam (params.IsVSyncOn);
201
mySettings->saveParam (params.ToLimitFps);
202
+ mySettings->saveParam (params.ToSmoothUploads);
203
mySettings->saveParam (params.UseGpu);
204
mySettings->saveParam (params.UseOpenJpeg);
205
if(!params.IsLocalWebUI->getValue()) {
206
207
}
208
209
myGUI->stglInit();
210
+ StRectF_t aFrustL, aFrustR;
211
+ if(myWindow->getCustomProjection(aFrustL, aFrustR)) {
212
+ myGUI->changeCamera()->setCustomProjection(aFrustL, aFrustR);
213
+ } else {
214
+ myGUI->changeCamera()->resetCustomProjection();
215
+ }
216
myGUI->stglResize(myWindow->stglViewport(ST_WIN_MASTER), myWindow->getMargins(), (float )myWindow->stglAspectRatio());
217
218
for(size_t anIter = 0; anIter < myGUI->myImage->getActions().size(); ++anIter) {
219
220
return;
221
}
222
223
+ const bool isReadOnly = StFileNode::isFileReadOnly(myFileToDelete->getPath());
224
const StString aText = myLangMap->getValue(StMoviePlayerStrings::DIALOG_DELETE_FILE_QUESTION)
225
+ + (isReadOnly ? "\nWARNING! The file is READ ONLY!" : "")
226
+ "\n" + myFileToDelete->getPath();
227
228
StGLMessageBox* aDialog = new StGLMessageBox(myGUI.access(), myLangMap->getValue(StMoviePlayerStrings::DIALOG_DELETE_FILE_TITLE),
229
230
return;
231
}
232
233
+ StFileNode::removeReadOnlyFlag(myFileToDelete->getPath());
234
myVideo->doRemovePhysically(myFileToDelete);
235
myFileToDelete.nullify();
236
}
237
238
myVideo->params.UseOpenJpeg = params.UseOpenJpeg;
239
myVideo->params.ToSearchSubs = params.ToSearchSubs;
240
myVideo->params.ToTrackHeadAudio = params.ToTrackHeadAudio;
241
+ myVideo->params.SlideShowDelay = params.SlideShowDelay;
242
+ myVideo->setSwapJPS(params.ToSwapJPS->getValue());
243
myVideo->setStickPano360(params.ToStickPanorama->getValue());
244
myVideo->setForceBFormat(params.ToForceBFormat->getValue());
245
+ doChangeMixImagesVideos(params.ToMixImagesVideos->getValue());
246
247
#ifdef ST_HAVE_MONGOOSE
248
doStartWebUI();
249
250
// load this parameter AFTER video thread creation
251
mySettings->loadParam(params.SrcStereoFormat);
252
253
-#if !defined(ST_NO_UPDATES_CHECK)
254
+#if defined(ST_UPDATES_CHECK)
255
// read the current time
256
time_t aRawtime;
257
time(&aRawtime);
258
259
StArgument anArgBenchmark = theArguments[params.Benchmark->getKey()];
260
StArgument anArgShowMenu = theArguments[params.ToShowMenu->getKey()];
261
StArgument anArgShowTopbar = theArguments[params.ToShowTopbar->getKey()];
262
+ StArgument anArgMixImages = theArguments[params.ToMixImagesVideos->getKey()];
263
264
StArgument anArgFullscreen = theArguments[params.IsFullscreen->getKey()];
265
StArgument anArgMonitor = theArguments[ST_ARGUMENT_MONITOR];
266
267
if(anArgShowTopbar.isValid()) {
268
params.ToShowTopbar->setValue(!anArgShowTopbar.isValueOff());
269
}
270
+ if(anArgMixImages.isValid()) {
271
+ params.ToMixImagesVideos->setValue(!anArgMixImages.isValueOff());
272
+ }
273
}
274
275
bool StMoviePlayer::open() {
276
277
doOpenRecent(0); // open last opened file
278
if(isPaused) {
279
myVideo->pushPlayEvent(ST_PLAYEVENT_PAUSE);
280
+ } else if(!anArgLast.isValid() && !anArgPause.isValid() && !anArgPaused.isValid()) {
281
+ myVideo->pushPlayEvent(ST_PLAYEVENT_PAUSE);
282
}
283
}
284
return true;
285
286
myPlayList->clear();
287
288
//StArgument argFile1 = myOpenFileInfo->getArgumentsMap()[ST_ARGUMENT_FILE + 1]; // playlist?
289
- StArgument argFileLeft = myOpenFileInfo->getArgumentsMap()[ST_ARGUMENT_FILE_LEFT];
290
- StArgument argFileRight = myOpenFileInfo->getArgumentsMap()[ST_ARGUMENT_FILE_RIGHT];
291
+ const StArgument argFileLeft = myOpenFileInfo->getArgumentsMap()[ST_ARGUMENT_FILE_LEFT];
292
+ const StArgument argFileRight = myOpenFileInfo->getArgumentsMap()[ST_ARGUMENT_FILE_RIGHT];
293
+ const StArgument anArgSeek = myOpenFileInfo->getArgumentsMap()[ST_ARGUMENT_FILE_SEEK];
294
+ if(anArgSeek.isValid()) {
295
+ StCLocale aCLocale;
296
+ mySeekOnLoad = stStringToDouble(anArgSeek.getValue().toCString(), aCLocale);
297
+ }
298
if(argFileLeft.isValid() && argFileRight.isValid()) {
299
// meta-file
300
const size_t aRecent = myPlayList->findRecent(argFileLeft.getValue(), argFileRight.getValue());
301
302
}
303
myPlayList->addOneFile(argFileLeft.getValue(), argFileRight.getValue());
304
} else if(!anOpenMIME.isEmpty()) {
305
+ // handle URI with #t=SECONDS tail
306
+ StString aFilePath = myOpenFileInfo->getPath();
307
+ StHandle< StArrayList<StString> > anUriParams = aFilePath.split('#', 2);
308
+ if(anUriParams->size() == 2) {
309
+ aFilePath = anUriParams->getFirst();
310
+ StString aParams = anUriParams->getLast();
311
+ if(aParams.isStartsWith(stCString("t="))) {
312
+ StCLocale aCLocale;
313
+ mySeekOnLoad = stStringToDouble(aParams.toCString() + 2, aCLocale);
314
+ }
315
+ }
316
+
317
// create just one-file playlist
318
myPlayList->addOneFile(myOpenFileInfo->getPath(), anOpenMIME);
319
} else {
320
+ // handle URI with #t=SECONDS tail
321
+ StString aFilePath = myOpenFileInfo->getPath();
322
+ double aSeekPos = -1.0;
323
+ StHandle< StArrayList<StString> > anUriParams = aFilePath.split('#', 2);
324
+ if(anUriParams->size() == 2) {
325
+ aFilePath = anUriParams->getFirst();
326
+ StString aParams = anUriParams->getLast();
327
+ if(aParams.isStartsWith(stCString("t="))) {
328
+ StCLocale aCLocale;
329
+ aSeekPos = stStringToDouble(aParams.toCString() + 2, aCLocale);
330
+ }
331
+ }
332
+
333
// create playlist from file's folder
334
- const size_t aRecent = myPlayList->findRecent(myOpenFileInfo->getPath());
335
+ const size_t aRecent = myPlayList->findRecent(aFilePath);
336
if(aRecent != size_t(-1)) {
337
doOpenRecent(aRecent);
338
+ if(aSeekPos >= 0.0) {
339
+ mySeekOnLoad = aSeekPos;
340
+ }
341
if(isPaused) {
342
myVideo->pushPlayEvent(ST_PLAYEVENT_PAUSE);
343
}
344
return true;
345
}
346
- myPlayList->open(myOpenFileInfo->getPath());
347
+ if(aSeekPos >= 0.0) {
348
+ mySeekOnLoad = aSeekPos;
349
+ }
350
+ myPlayList->open(aFilePath);
351
}
352
353
if(!myPlayList->isEmpty()) {
354
355
if(toMobileGui != wasMobileGui) {
356
doChangeMobileUI(params.IsMobileUI->getValue());
357
} else {
358
+ StRectF_t aFrustL, aFrustR;
359
+ if(myWindow->getCustomProjection(aFrustL, aFrustR)) {
360
+ myGUI->changeCamera()->setCustomProjection(aFrustL, aFrustR);
361
+ } else {
362
+ myGUI->changeCamera()->resetCustomProjection();
363
+ }
364
myGUI->stglResize(myWindow->stglViewport(ST_WIN_MASTER), myWindow->getMargins(), (float )myWindow->stglAspectRatio());
365
}
366
}
367
368
}
369
370
void StMoviePlayer::doGesture(const StGestureEvent& theEvent) {
371
- if(myGUI.isNull()
372
- || myGUI->myImage == NULL) {
373
- return;
374
- }
375
-
376
- for(StGLWidget *aChildIter(myGUI->getChildren()->getLast()), *aChildActive(NULL); aChildIter != NULL;) {
377
- aChildActive = aChildIter;
378
- aChildIter = aChildIter->getPrev();
379
- if(aChildActive->isVisibleAndPointIn(myGUI->getCursorZo())) {
380
- if(aChildActive == myGUI->myImage) {
381
- myGUI->myImage->doGesture(theEvent);
382
- }
383
- break;
384
- }
385
+ if(!myGUI.isNull()) {
386
+ myGUI->doGesture(theEvent);
387
}
388
}
389
390
391
return;
392
}
393
394
+ // handle URI with #t=SECONDS tail
395
+ double aSeekPos = -1.0;
396
+ StHandle< StArrayList<StString> > anUriParams = aText.split('#', 2);
397
+ if(anUriParams->size() == 2) {
398
+ aText = anUriParams->getFirst();
399
+ StString aParams = anUriParams->getLast();
400
+ if(aParams.isStartsWith(stCString("t="))) {
401
+ StCLocale aCLocale;
402
+ aSeekPos = stStringToDouble(aParams.toCString() + 2, aCLocale);
403
+ }
404
+ }
405
+
406
const size_t aRecent = myPlayList->findRecent(aText);
407
if(aRecent != size_t(-1)) {
408
doOpenRecent(aRecent);
409
+ if(aSeekPos >= 0.0) {
410
+ mySeekOnLoad = aSeekPos;
411
+ }
412
return;
413
}
414
+
415
+ if(aSeekPos >= 0.0) {
416
+ mySeekOnLoad = aSeekPos;
417
+ }
418
myPlayList->open(aText);
419
if(!myPlayList->isEmpty()) {
420
doUpdateStateLoading();
421
422
return;
423
}
424
425
+ if(!myPlayList->checkExtension(aFile1)
426
+ && myVideo->getMimeListImages().checkExtension(anExt1)) {
427
+ // redirect to StMoviePlayer
428
+ myOpenFileOtherApp = new StOpenInfo();
429
+ StArgumentsMap anArgs;
430
+ anArgs.add(StArgument("in", "image"));
431
+ myOpenFileOtherApp->setArgumentsMap(anArgs);
432
+ myOpenFileOtherApp->setPath(aFile1);
433
+ exit(0);
434
+ return;
435
+ }
436
+
437
// just open the path
438
- //if(myPlayList->checkExtension(aFile1)) {
439
- const size_t aRecent = myPlayList->findRecent(aFile1);
440
- if(aRecent != size_t(-1)) {
441
- doOpenRecent(aRecent);
442
- return;
443
- }
444
+ const size_t aRecent = myPlayList->findRecent(aFile1);
445
+ if(aRecent != size_t(-1)) {
446
+ doOpenRecent(aRecent);
447
+ return;
448
+ }
449
450
- myPlayList->open(aFile1);
451
- doUpdateStateLoading();
452
- myVideo->pushPlayEvent(ST_PLAYEVENT_RESUME);
453
- myVideo->doLoadNext();
454
- //}
455
+ myPlayList->open(aFile1);
456
+ doUpdateStateLoading();
457
+ myVideo->pushPlayEvent(ST_PLAYEVENT_RESUME);
458
+ myVideo->doLoadNext();
459
return;
460
} else if(theEvent.NbFiles == 2
461
&& !StFolder::isFolder(aFile2)
462
463
myPlayList->addOneFile(aPath, StMIME());
464
}
465
}
466
+
467
doUpdateStateLoading();
468
myVideo->pushPlayEvent(ST_PLAYEVENT_RESUME);
469
myVideo->doLoadNext();
470
471
myPlayList->clear();
472
myPlayList->addOneFile(myOpenDialog->getPathLeft(), myOpenDialog->getPathRight());
473
} else {
474
- aFilePath = myOpenDialog->getPathLeft();
475
- myPlayList->open(myOpenDialog->getPathLeft());
476
+ if(!myPlayList->checkExtension(myOpenDialog->getPathLeft())
477
+ && myVideo->getMimeListImages().checkExtension(StFileNode::getExtension(myOpenDialog->getPathLeft()))) {
478
+ // redirect to StImageViewer
479
+ myOpenFileOtherApp = new StOpenInfo();
480
+ StArgumentsMap anArgs;
481
+ anArgs.add(StArgument("in", "image"));
482
+ myOpenFileOtherApp->setArgumentsMap(anArgs);
483
+ myOpenFileOtherApp->setPath(myOpenDialog->getPathLeft());
484
+ exit(0);
485
+ } else {
486
+ aFilePath = myOpenDialog->getPathLeft();
487
+ myPlayList->open(myOpenDialog->getPathLeft());
488
+ }
489
}
490
491
doUpdateStateLoading();
492
493
}
494
myWindow->setStereoOutput(hasStereoSource);
495
496
+ const double aDispMaxFps = myWindow->getMaximumTargetFps();
497
+ double aTargetFps = myVideo->getAverFps();
498
+ int aMaxUploadFrames = int((double(aDispMaxFps) + 0.1) / stMax(aTargetFps, 1.0));
499
if(params.Benchmark->getValue()
500
|| !params.ToLimitFps->getValue()) {
501
// do not limit FPS
502
503
} else if(params.TargetFps->getValue() >= 1
504
&& params.TargetFps->getValue() <= 3) {
505
// set rendering FPS to 2x averageFPS
506
- double aTargetFps = myVideo->getAverFps();
507
+ const bool toTrackOrientation = myWindow->toTrackOrientation();
508
if(aTargetFps < 17.0
509
|| aTargetFps > 120.0) {
510
aTargetFps = 0.0;
511
} else if(aTargetFps < 40.0) {
512
+ if(!toTrackOrientation) {
513
+ aMaxUploadFrames = 2; // maximum 2 frames to upload single frame
514
+ }
515
aTargetFps *= double(params.TargetFps->getValue());
516
+ } else {
517
+ if(!toTrackOrientation) {
518
+ aMaxUploadFrames = 1; // uploads should be done within single frame
519
+ }
520
}
521
522
- if(myWindow->toTrackOrientation()) {
523
+ if(toTrackOrientation) {
524
// do not limit FPS within head-tracking mode
525
aTargetFps = 0.0;
526
+ } else if(aTargetFps > aDispMaxFps) {
527
+ aTargetFps = 0.0;
528
}
529
530
myWindow->setTargetFps(aTargetFps);
531
} else {
532
// set rendering FPS to set value in settings
533
myWindow->setTargetFps(double(params.TargetFps->getValue()));
534
+ aMaxUploadFrames = 1; // uploads should be done within single frame
535
}
536
537
+ if(!params.ToSmoothUploads->getValue()) {
538
+ aMaxUploadFrames = 1;
539
+ }
540
+ myVideo->getTextureQueue()->getUploadParams().MaxUploadIterations = stMax(stMin(aMaxUploadFrames, 3), 1);
541
}
542
543
void StMoviePlayer::doUpdateOpenALDeviceList(const size_t ) {
544
545
}
546
}
547
548
+void StMoviePlayer::doSwitchViewMode(const int32_t theMode) {
549
+ if(myVideo.isNull()) {
550
+ return;
551
+ }
552
+
553
+ myVideo->setTheaterMode(theMode == StViewSurface_Theater);
554
+}
555
+
556
void StMoviePlayer::doPanoramaOnOff(const size_t ) {
557
if(myVideo.isNull()) {
558
return;
559
560
StPanorama aPano = st::probePanorama(aParams->StereoFormat,
561
aParams->Src1SizeX, aParams->Src1SizeY,
562
aParams->Src2SizeX, aParams->Src2SizeY);
563
- myGUI->myImage->params.ViewMode->setValue(aPano == StPanorama_Cubemap6_1 || aPano == StPanorama_Cubemap3_2
564
- ? StViewSurface_Cubemap
565
- : StViewSurface_Sphere);
566
+ myGUI->myImage->params.ViewMode->setValue(StStereoParams::getViewSurfaceForPanoramaSource(aPano, true));
567
}
568
569
void StMoviePlayer::doChangeStickPano360(const bool ) {
570
571
myVideo->setStickPano360(params.ToStickPanorama->getValue());
572
}
573
574
+void StMoviePlayer::doChangeSwapJPS(const bool ) {
575
+ if(myVideo.isNull()) {
576
+ return;
577
+ }
578
+
579
+ myVideo->setSwapJPS(params.ToSwapJPS->getValue());
580
+}
581
+
582
void StMoviePlayer::doSwitchSrcFormat(const int32_t theSrcFormat) {
583
myVideo->setStereoFormat(StFormat(theSrcFormat));
584
double aDuration = 0.0;
585
586
}
587
}
588
589
+void StMoviePlayer::doSetStereoOutput(const size_t theMode) {
590
+ if(myVideo.isNull()) {
591
+ return;
592
+ }
593
+ myGUI->myImage->params.DisplayMode->setValue((int32_t )theMode);
594
+}
595
+
596
void StMoviePlayer::doScaleGui(const int32_t ) {
597
if(myGUI.isNull()) {
598
return;
599
600
myToRecreateMenu = true;
601
}
602
603
+void StMoviePlayer::doChangeMixImagesVideos(const bool theToMix) {
604
+ if(myVideo.isNull()) {
605
+ return;
606
+ }
607
+ if(theToMix) {
608
+ StArrayList<StString> aMediaExt = myVideo->getMimeListVideo().getExtensionsList();
609
+ StArrayList<StString> anImgExt = myVideo->getMimeListImages().getExtensionsList();
610
+ for(size_t anExtIter = 0; anExtIter < anImgExt.size(); ++anExtIter) {
611
+ aMediaExt.add(anImgExt.getValue(anExtIter));
612
+ }
613
+ myPlayList->setExtensions(aMediaExt);
614
+ } else {
615
+ myPlayList->setExtensions(myVideo->getMimeListVideo().getExtensionsList());
616
+ }
617
+}
618
+
619
void StMoviePlayer::doLoaded() {
620
myEventLoaded.set();
621
}
622
623
}
624
}
625
626
+void StMoviePlayer::doShowHideGUI(const size_t ) {
627
+ const bool toShow = !params.ToShowMenu->getValue() || (!myGUI.isNull() && !myGUI->isVisibleGUI());
628
+ params.ToShowMenu->setValue(toShow);
629
+ params.ToShowTopbar->setValue(toShow);
630
+ params.ToShowBottom->setValue(toShow);
631
+ if(toShow && !myGUI.isNull()) {
632
+ myGUI->setVisibility(myWindow->getMousePos(), false, true);
633
+ }
634
+}
635
+
636
void StMoviePlayer::doQuit(const size_t ) {
637
StApplication::exit(0);
638
}
639
640
void StMoviePlayer::doOpen1FileFromGui(StHandle<StString> thePath) {
641
- myOpenDialog->setPaths(*thePath, "");
642
+ myOpenDialog->setPaths(*thePath, "", StMovieOpenDialog::Dialog_SingleMovie);
643
+}
644
+
645
+void StMoviePlayer::doOpen1AudioFromGui(StHandle<StString> thePath) {
646
+ myOpenDialog->setPaths(*thePath, "", StMovieOpenDialog::Dialog_Audio);
647
+}
648
+
649
+void StMoviePlayer::doOpen1SubtitleFromGui(StHandle<StString> thePath) {
650
+ myOpenDialog->setPaths(*thePath, "", StMovieOpenDialog::Dialog_Subtitles);
651
}
652
653
void StMoviePlayer::doOpen1FileAction(const size_t ) {
654
if(!myGUI.isNull() && (myWindow->isFullScreen() || myGUI->isMobile())) {
655
- myGUI->doOpenFile(0);
656
+ myGUI->doOpenFile(StMovieOpenDialog::Dialog_SingleMovie);
657
return;
658
}
659
myOpenDialog->openDialog(StMovieOpenDialog::Dialog_SingleMovie);
660
}
661
662
void StMoviePlayer::doOpen2Files(const size_t ) {
663
+ if(!myGUI.isNull() && (myWindow->isFullScreen() || myGUI->isMobile())) {
664
+ //myGUI->doOpenFile(StMovieOpenDialog::Dialog_DoubleMovie);
665
+ //return;
666
+ }
667
myOpenDialog->openDialog(StMovieOpenDialog::Dialog_DoubleMovie);
668
}
669
670
671
}
672
673
void StMoviePlayer::doAddAudioStream(const size_t ) {
674
+ if(!myGUI.isNull() && (myWindow->isFullScreen() || myGUI->isMobile())) {
675
+ myGUI->doOpenFile(StMovieOpenDialog::Dialog_Audio);
676
+ return;
677
+ }
678
myOpenDialog->openDialog(StMovieOpenDialog::Dialog_Audio);
679
}
680
681
void StMoviePlayer::doAddSubtitleStream(const size_t ) {
682
+ if(!myGUI.isNull() && (myWindow->isFullScreen() || myGUI->isMobile())) {
683
+ myGUI->doOpenFile(StMovieOpenDialog::Dialog_Subtitles);
684
+ return;
685
+ }
686
myOpenDialog->openDialog(StMovieOpenDialog::Dialog_Subtitles);
687
}
688
689
690
691
void StMoviePlayer::doFullscreen(const bool theIsFullscreen) {
692
if(!myWindow.isNull()) {
693
+ myWindow->setAttribute(StWinAttr_ExclusiveFullScreen, params.IsExclusiveFullScreen->getValue());
694
myWindow->setFullScreen(theIsFullscreen);
695
}
696
}
697
698
const long aVol = stStringToLong(aQuery.toCString(), 10, aCLocale);
699
params.AudioGain->setValue(volumeToGain(params.AudioGain, GLfloat(aVol) * 0.01f));
700
aContent = "audio set volume...";
701
+ } else if(anURI.isEquals(stCString("/seek"))) {
702
+ StCLocale aCLocale;
703
+ const double aPosSec = stStringToDouble(aQuery.toCString(), aCLocale);
704
+ myVideo->pushPlayEvent(ST_PLAYEVENT_SEEK, aPosSec);
705
+ aContent = "seek to position...";
706
} else if(anURI.isEquals(stCString("/fullscr_win"))) {
707
invokeAction(Action_Fullscreen);
708
aContent = "switch fullscreen/windowed...";
709
sview-17_04.tar.gz/StMoviePlayer/StMoviePlayer.h -> sview-20_08.tar.gz/StMoviePlayer/StMoviePlayer.h
Changed
87
1
2
/**
3
- * Copyright © 2007-2017 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2007-2020 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* StMoviePlayer program is free software: you can redistribute it and/or modify
7
* it under the terms of the GNU General Public License as published by
8
9
ST_LOCAL void doSubtitlesNext(size_t theDirection);
10
ST_LOCAL void doSubtitlesCopy(size_t dummy = 0);
11
ST_LOCAL void doFromClipboard(size_t dummy = 0);
12
+ ST_LOCAL void doShowHideGUI(const size_t dummy = 0);
13
14
ST_LOCAL void doQuit(const size_t dummy = 0);
15
16
ST_LOCAL void doFileNext();
17
ST_LOCAL void doOpen1FileFromGui(StHandle<StString> thePath);
18
+ ST_LOCAL void doOpen1AudioFromGui(StHandle<StString> thePath);
19
+ ST_LOCAL void doOpen1SubtitleFromGui(StHandle<StString> thePath);
20
ST_LOCAL void doOpen1FileAction(const size_t dummy = 0);
21
ST_LOCAL void doOpen2Files(const size_t dummy = 0);
22
ST_LOCAL void doSaveFileInfo(const size_t theToSave);
23
24
StHandle<StFloat32Param> SubtitlesParallax; //!< subtitles parallax
25
StHandle<StBoolParamNamed> ToSearchSubs; //!< automatically search for additional subtitles/audio track files nearby video file
26
StHandle<StEnumParam> SubtitlesParser; //!< subtitles parser
27
+ StHandle<StBoolParamNamed> SubtitlesApplyStereo; //!< apply stereoscopic format of video to image subtitles
28
StHandle<StALDeviceParam> AudioAlDevice; //!< active OpenAL device
29
StHandle<StEnumParam> AudioAlHrtf; //!< OpenAL HRTF flag
30
StHandle<StFloat32Param> AudioGain; //!< volume factor
31
32
StHandle<StEnumParam> CheckUpdatesDays; //!< days count between updates checks
33
StHandle<StInt32ParamNamed> LastUpdateDay; //!< the last time update has been checked
34
StHandle<StInt32ParamNamed> SrcStereoFormat; //!< source format
35
+ StHandle<StBoolParamNamed> ToSwapJPS; //!< swap JPS views order
36
StHandle<StBoolParamNamed> ToStickPanorama; //!< force panorama input for all files
37
StHandle<StBoolParamNamed> ToTrackHead; //!< enable/disable head-tracking
38
StHandle<StBoolParamNamed> ToTrackHeadAudio; //!< enable/disable head-tracking for audio listener
39
40
StHandle<StBoolParamNamed> ToShowFps; //!< display FPS meter
41
StHandle<StBoolParamNamed> ToShowMenu; //!< show main menu
42
StHandle<StBoolParamNamed> ToShowTopbar; //!< show topbar
43
+ StHandle<StBoolParamNamed> ToShowBottom; //!< show bottom (seekbar)
44
+ StHandle<StBoolParamNamed> ToMixImagesVideos; //!< mix videos and images
45
+ StHandle<StFloat32Param> SlideShowDelay; //!< slideshow delay
46
StHandle<StBoolParamNamed> IsMobileUI; //!< display mobile interface (user option)
47
StHandle<StBoolParam> IsMobileUISwitch; //!< display mobile interface (actual value)
48
+ StHandle<StBoolParamNamed> IsExclusiveFullScreen; //!< exclusive fullscreen mode
49
StHandle<StBoolParamNamed> ToLimitFps; //!< limit CPU usage or not
50
+ StHandle<StBoolParamNamed> ToSmoothUploads; //!< smooth texture uploads
51
StHandle<StBoolParamNamed> IsVSyncOn; //!< flag to use VSync
52
StHandle<StEnumParam> StartWebUI; //!< to start Web UI or not
53
StHandle<StBoolParamNamed> ToPrintWebErrors; //!< print Web UI starting errors
54
55
ST_LOCAL void doScaleGui(const int32_t );
56
ST_LOCAL void doChangeMobileUI(const bool );
57
ST_LOCAL void doScaleHiDPI(const bool );
58
+ ST_LOCAL void doChangeMixImagesVideos(const bool );
59
ST_LOCAL void doSwitchVSync(const bool theValue);
60
ST_LOCAL void doSwitchAudioDevice(const int32_t theDevId);
61
ST_LOCAL void doSwitchAudioAlHrtf(const int32_t theValue);
62
63
ST_LOCAL void doSwitchLoopSingle(const bool theValue);
64
ST_LOCAL void doFullscreen(const bool theIsFullscreen);
65
ST_LOCAL void doSwitchSrcFormat(const int32_t theSrcFormat);
66
+ ST_LOCAL void doSetStereoOutput(const size_t theMode);
67
+ ST_LOCAL void doSwitchViewMode(const int32_t theMode);
68
ST_LOCAL void doPanoramaOnOff(const size_t );
69
ST_LOCAL void doChangeStickPano360(const bool );
70
+ ST_LOCAL void doChangeSwapJPS(const bool );
71
ST_LOCAL void doSwitchAudioStream(const int32_t theStreamId);
72
ST_LOCAL void doSwitchSubtitlesStream(const int32_t theStreamId);
73
ST_LOCAL void doShowPlayList(const bool theToShow);
74
75
Action_StereoParamsBegin,
76
Action_StereoParamsEnd = Action_StereoParamsBegin + StGLImageRegion::ActionsNb - 1,
77
Action_PanoramaOnOff,
78
+ Action_ShowGUI,
79
+ Action_OutStereoNormal,
80
+ Action_OutStereoLeftView,
81
+ Action_OutStereoRightView,
82
+ Action_OutStereoParallelPair,
83
+ Action_OutStereoCrossEyed,
84
};
85
86
private: //! @name Web UI methods
87
sview-17_04.tar.gz/StMoviePlayer/StMoviePlayer.rc -> sview-20_08.tar.gz/StMoviePlayer/StMoviePlayer.rc
Changed
10
1
2
BEGIN
3
VALUE "FileDescription", "Stereoscopic Movie Player\000"
4
VALUE "FileVersion", SVIEW_SDK_VER_STRING "\000"
5
- VALUE "LegalCopyright", "\251 2007-2017 Kirill Gavrilov\000"
6
+ VALUE "LegalCopyright", "\251 2007-2020 Kirill Gavrilov and sView developers\000"
7
VALUE "ProductName", "StMoviePlayer\000"
8
VALUE "ProductVersion", SVIEW_SDK_VER_STRING "\000"
9
VALUE "OfficialSite", "www.sview.ru\000"
10
sview-17_04.tar.gz/StMoviePlayer/StMoviePlayerGUI.cpp -> sview-20_08.tar.gz/StMoviePlayer/StMoviePlayerGUI.cpp
Changed
721
1
2
/**
3
- * Copyright © 2009-2017 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2009-2020 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* StMoviePlayer program is free software: you can redistribute it and/or modify
7
* it under the terms of the GNU General Public License as published by
8
9
10
#include "StVideo/StALContext.h"
11
#include "StVideo/StVideo.h"
12
+#include "StMovieOpenDialog.h"
13
14
#include <StCore/StSearchMonitors.h>
15
#include <StImage/StImageFile.h>
16
17
18
namespace {
19
20
+ static const float THE_VISIBILITY_IDLE_TIME = 2.0f;
21
+
22
static const int DISPL_Y_REGION_UPPER = 32;
23
static const int DISPL_X_REGION_UPPER = 32;
24
static const int DISPL_X_REGION_BOTTOM = 52;
25
26
const int anIconStep = scale(48);
27
aButtonMargins.extend(scale(8));
28
29
- myPanelUpper = new StGLContainer(this, 0, 0, StGLCorner(ST_VCORNER_TOP, ST_HCORNER_LEFT), scale(4096), scale(128));
30
+ myPanelUpper = new StGLContainer(this, aLeft, aTop, StGLCorner(ST_VCORNER_TOP, ST_HCORNER_LEFT), scale(4096), scale(128));
31
32
// append the textured buttons
33
- myBtnOpen = new StGLTextureButton(myPanelUpper, aLeft + (aBtnIter++) * anIconStep, aTop);
34
+ myBtnOpen = new StGLTextureButton(myPanelUpper, (aBtnIter++) * anIconStep, 0);
35
myBtnOpen->signals.onBtnClick.connect(myPlugin, &StMoviePlayer::doOpen1FileAction);
36
myBtnOpen->setTexturePath(iconTexture(stCString("actionOpen"), anIconSize));
37
myBtnOpen->setDrawShadow(true);
38
myBtnOpen->changeMargins() = aButtonMargins;
39
40
- myBtnInfo = new StGLTextureButton(myPanelUpper, aLeft + (aBtnIter++) * anIconStep, aTop);
41
+ myBtnInfo = new StGLTextureButton(myPanelUpper, (aBtnIter++) * anIconStep, 0);
42
myBtnInfo->signals.onBtnClick += stSlot(myPlugin, &StMoviePlayer::doAboutFile);
43
myBtnInfo->setTexturePath(iconTexture(stCString("actionInfo"), anIconSize));
44
myBtnInfo->setDrawShadow(true);
45
myBtnInfo->changeMargins() = aButtonMargins;
46
47
- StGLTextureButton* aSrcBtn = new StGLTextureButton(myPanelUpper, aLeft + (aBtnIter++) * anIconStep, aTop,
48
+ StGLTextureButton* aSrcBtn = new StGLTextureButton(myPanelUpper, (aBtnIter++) * anIconStep, 0,
49
StGLCorner(ST_VCORNER_TOP, ST_HCORNER_LEFT), StFormat_NB + 1);
50
aSrcBtn->changeMargins() = aButtonMargins;
51
aSrcBtn->signals.onBtnClick += stSlot(this, &StMoviePlayerGUI::doDisplayStereoFormatCombo);
52
53
myBtnSwapLR = new StGLCheckboxTextured(myPanelUpper, myImage->params.SwapLR,
54
iconTexture(stCString("actionSwapLROff"), anIconSize),
55
iconTexture(stCString("actionSwapLROn"), anIconSize),
56
- aLeft + (aBtnIter++) * anIconStep, aTop,
57
+ (aBtnIter++) * anIconStep, 0,
58
StGLCorner(ST_VCORNER_TOP, ST_HCORNER_LEFT));
59
myBtnSwapLR->setDrawShadow(true);
60
myBtnSwapLR->changeMargins() = aButtonMargins;
61
62
myBtnPanorama = new StGLCheckboxTextured(myPanelUpper, aTrackedPano,
63
iconTexture(stCString("actionPanoramaOff"), anIconSize),
64
iconTexture(stCString("actionPanorama"), anIconSize),
65
- aLeft + (aBtnIter++) * anIconStep, aTop,
66
+ (aBtnIter++) * anIconStep, 0,
67
StGLCorner(ST_VCORNER_TOP, ST_HCORNER_LEFT));
68
myBtnPanorama->signals.onBtnClick += stSlot(this, &StMoviePlayerGUI::doPanoramaCombo);
69
myBtnPanorama->setDrawShadow(true);
70
71
myBtnAdjust = new StGLCheckboxTextured(myPanelUpper, myPlugin->params.ToShowAdjustImage,
72
iconTexture(stCString("actionColorAdjustOff"), anIconSize),
73
iconTexture(stCString("actionColorAdjust"), anIconSize),
74
- aLeft + (aBtnIter++) * anIconStep, aTop,
75
+ (aBtnIter++) * anIconStep, 0,
76
StGLCorner(ST_VCORNER_TOP, ST_HCORNER_LEFT));
77
myBtnAdjust->setDrawShadow(true);
78
myBtnAdjust->changeMargins() = aButtonMargins;
79
80
myBtnSubs = new StGLCheckboxTextured(myPanelUpper, aTrackedSubs,
81
iconTexture(stCString("actionStreamSubtitlesOff"), anIconSize),
82
iconTexture(stCString("actionStreamSubtitles"), anIconSize),
83
- (aNbBtnRight++) * (-anIconStep) - aLeft, aTop,
84
+ (aNbBtnRight++) * (-anIconStep), 0,
85
StGLCorner(ST_VCORNER_TOP, ST_HCORNER_RIGHT));
86
myBtnSubs->signals.onBtnClick = stSlot(this, &StMoviePlayerGUI::doSubtitlesStreamsCombo);
87
myBtnSubs->setDrawShadow(true);
88
89
myBtnAudio = new StGLCheckboxTextured(myPanelUpper, aTrackedAudio,
90
iconTexture(stCString("actionStreamAudioOff"), anIconSize),
91
iconTexture(stCString("actionStreamAudio"), anIconSize),
92
- (aNbBtnRight++) * (-anIconStep) - aLeft, aTop,
93
+ (aNbBtnRight++) * (-anIconStep), 0,
94
StGLCorner(ST_VCORNER_TOP, ST_HCORNER_RIGHT));
95
myBtnAudio->signals.onBtnClick = stSlot(this, &StMoviePlayerGUI::doAudioStreamsCombo);
96
myBtnAudio->setDrawShadow(true);
97
98
void StMoviePlayerGUI::fillPanoramaMenu(StGLMenu* theMenu) {
99
theMenu->addItem(tr(MENU_VIEW_SURFACE_PLANE),
100
myImage->params.ViewMode, StViewSurface_Plain);
101
+ theMenu->addItem(tr(MENU_VIEW_SURFACE_THEATER),
102
+ myImage->params.ViewMode, StViewSurface_Theater);
103
+ theMenu->addItem(tr(MENU_VIEW_SURFACE_CYLINDER),
104
+ myImage->params.ViewMode, StViewSurface_Cylinder);
105
+ theMenu->addItem(tr(MENU_VIEW_SURFACE_HEMISPHERE),
106
+ myImage->params.ViewMode, StViewSurface_Hemisphere);
107
theMenu->addItem(tr(MENU_VIEW_SURFACE_SPHERE),
108
myImage->params.ViewMode, StViewSurface_Sphere);
109
theMenu->addItem(tr(MENU_VIEW_SURFACE_CUBEMAP),
110
myImage->params.ViewMode, StViewSurface_Cubemap);
111
+ theMenu->addItem(tr(MENU_VIEW_SURFACE_CUBEMAP_EAC),
112
+ myImage->params.ViewMode, StViewSurface_CubemapEAC);
113
if(myWindow->hasOrientationSensor()) {
114
theMenu->addItem(tr(myWindow->isPoorOrientationSensor() ? MENU_VIEW_TRACK_HEAD_POOR : MENU_VIEW_TRACK_HEAD),
115
myPlugin->params.ToTrackHead);
116
117
myImage->params.TextureFilter, StGLImageProgram::FILTER_NEAREST);
118
aMenu->addItem(tr(MENU_VIEW_TEXFILTER_LINEAR),
119
myImage->params.TextureFilter, StGLImageProgram::FILTER_LINEAR);
120
+ aMenu->addItem(tr(MENU_VIEW_TEXFILTER_TRILINEAR),
121
+ myImage->params.TextureFilter, StGLImageProgram::FILTER_TRILINEAR);
122
aMenu->addItem(tr(MENU_VIEW_TEXFILTER_BLEND),
123
myImage->params.TextureFilter, StGLImageProgram::FILTER_BLEND);
124
return aMenu;
125
126
127
StDelayControl(StMoviePlayerGUI* theParent,
128
const StHandle<StFloat32Param>& theTrackedValue)
129
- : StGLMessageBox(theParent, theParent->tr(DIALOG_AUDIO_DELAY_TITLE), "", theParent->scale(400), theParent->scale(260)),
130
+ : StGLMessageBox(theParent),
131
myRange(NULL) {
132
- changeRectPx().moveX( myRoot->scale( 64));
133
- changeRectPx().moveY(-myRoot->scale(128));
134
+ int aWidth = stMin(theParent->scale(400), myRoot->getRectPx().width());
135
+ int aHeight = stMin(theParent->scale(220), myRoot->getRectPx().height());
136
+ const bool isCompact = myRoot->getRectPx().width() <= myRoot->scale(450)
137
+ || myRoot->getRectPx().height() <= myRoot->scale(450);
138
+ if(isCompact) {
139
+ aHeight = stMin(theParent->scale(150), aHeight);
140
+ } else {
141
+ changeRectPx().left() = myRoot->scale(64);
142
+ changeRectPx().top() = -myRoot->scale(128);
143
+ }
144
setCorner(StGLCorner(ST_VCORNER_BOTTOM, ST_HCORNER_LEFT));
145
+ changeRectPx().right() = getRectPx().left() + aWidth;
146
+ changeRectPx().bottom() = getRectPx().top() + aHeight;
147
+ create(theParent->tr(DIALOG_AUDIO_DELAY_TITLE), "", aWidth, aHeight);
148
+ if(isCompact) {
149
+ myMinSizeY = theParent->scale(150);
150
+ }
151
+
152
StGLButton* aResetBtn = addButton(theParent->tr(BUTTON_RESET));
153
addButton(theParent->tr(BUTTON_CLOSE));
154
155
156
const StGLVec3 THE_WHITE(1.0f, 1.0f, 1.0f);
157
const StString anAbout = tr(ABOUT_DPLUGIN_NAME) + '\n'
158
+ tr(ABOUT_VERSION) + " " + StVersionInfo::getSDKVersionString()
159
- + "\n \n" + tr(ABOUT_DESCRIPTION).format("2007-2017", "kirill@sview.ru", "www.sview.ru")
160
+ + "\n \n" + tr(ABOUT_DESCRIPTION).format("2007-2020", "kirill@sview.ru", "www.sview.ru")
161
+ "\n\n<b><i>Used projects</i></b>"
162
+ "\n \nFFmpeg " + stAV::getVersionInfo() + " (" + stAV::getLicenseInfo() + ")\nhttps://ffmpeg.org/"
163
+ "\n \nOpenAL Soft (LGPL)\nhttp://kcat.strangesoft.net/openal.html"
164
165
const IconSize anIconSize = scaleIcon(32, aButtonMargins);
166
aButtonMargins.extend(scale(12));
167
168
+ ///
169
+ ///const int aBotOffset = scale(56);
170
myPanelBottom = new StGLContainer(this, 0, 0, StGLCorner(ST_VCORNER_BOTTOM, ST_HCORNER_LEFT), scale(4096), scale(56));
171
172
const StGLCorner aLeftCorner = StGLCorner(ST_VCORNER_TOP, ST_HCORNER_LEFT);
173
174
myBtnReset3d->changeMargins() = aButtonMargins;
175
}
176
177
-void StMoviePlayerGUI::doOpenFile(const size_t ) {
178
- StGLOpenFile* aDialog = new StGLOpenFile(this, tr(DIALOG_OPEN_FILE), tr(BUTTON_CLOSE));
179
- aDialog->setMimeList(myPlugin->myVideo->getMimeListVideo());
180
-#if defined(_WIN32)
181
- //
182
-#else
183
- aDialog->addHotItem("/", "Root");
184
-#endif
185
- aDialog->addHotItem(getResourceManager()->getFolder(StResourceManager::FolderId_SdCard));
186
+void StMoviePlayerGUI::doOpenFile(const size_t theFileType) {
187
+ StString aTitle;
188
+ switch(theFileType) {
189
+ case StMovieOpenDialog::Dialog_Audio: {
190
+ aTitle = tr(DIALOG_OPEN_AUDIO);
191
+ break;
192
+ }
193
+ case StMovieOpenDialog::Dialog_Subtitles: {
194
+ aTitle = tr(DIALOG_OPEN_SUBTITLES);
195
+ break;
196
+ }
197
+ case StMovieOpenDialog::Dialog_SingleMovie:
198
+ case StMovieOpenDialog::Dialog_DoubleMovie:
199
+ default: {
200
+ aTitle = tr(DIALOG_OPEN_FILE);
201
+ break;
202
+ }
203
+ }
204
+
205
+ StGLOpenFile* aDialog = new StGLOpenFile(this, aTitle, tr(BUTTON_CLOSE));
206
+ const StString anSdCardPath = getResourceManager()->getFolder(StResourceManager::FolderId_SdCard);
207
+ if(!anSdCardPath.isEmpty()) {
208
+ StString aFolder, aName;
209
+ StFileNode::getFolderAndFile(anSdCardPath, aFolder, aName);
210
+ aDialog->addHotItem(anSdCardPath, stUtfTools::isInteger(aName) ? (StString("sdcard") + aName) : aName);
211
+ }
212
aDialog->addHotItem(getResourceManager()->getFolder(StResourceManager::FolderId_Downloads));
213
+ aDialog->addHotItem(getResourceManager()->getFolder(StResourceManager::FolderId_Documents));
214
aDialog->addHotItem(getResourceManager()->getFolder(StResourceManager::FolderId_Videos));
215
aDialog->addHotItem(getResourceManager()->getFolder(StResourceManager::FolderId_Music));
216
- aDialog->signals.onFileSelected = stSlot(myPlugin, &StMoviePlayer::doOpen1FileFromGui);
217
+
218
+ switch(theFileType) {
219
+ case StMovieOpenDialog::Dialog_Audio: {
220
+ aDialog->signals.onFileSelected = stSlot(myPlugin, &StMoviePlayer::doOpen1AudioFromGui);
221
+ aDialog->setMimeList(myPlugin->myVideo->getMimeListAudio(), "Audio", false);
222
+ break;
223
+ }
224
+ case StMovieOpenDialog::Dialog_Subtitles: {
225
+ aDialog->signals.onFileSelected = stSlot(myPlugin, &StMoviePlayer::doOpen1SubtitleFromGui);
226
+ aDialog->setMimeList(myPlugin->myVideo->getMimeListSubtitles(), "Subtitles", false);
227
+ break;
228
+ }
229
+ case StMovieOpenDialog::Dialog_SingleMovie:
230
+ case StMovieOpenDialog::Dialog_DoubleMovie:
231
+ default: {
232
+ aDialog->signals.onFileSelected = stSlot(myPlugin, &StMoviePlayer::doOpen1FileFromGui);
233
+ aDialog->setDisplayExtra(myPlugin->params.ToMixImagesVideos->getValue());
234
+ aDialog->setMimeList(myPlugin->myVideo->getMimeListVideo(), "Videos", false);
235
+ aDialog->setMimeList(myPlugin->myVideo->getMimeListImages(), "Images", true);
236
+ aDialog->addHotCheckbox(myPlugin->params.ToMixImagesVideos, myPlugin->params.ToMixImagesVideos->getName());
237
+ break;
238
+ }
239
+ }
240
241
if(myPlugin->params.lastFolder.isEmpty()) {
242
StHandle<StFileNode> aCurrFile = myPlugin->myPlayList->getCurrentFile();
243
244
anItem = aMenu->addItem(tr(BUTTON_DELETE), myPlugin->getAction(StMoviePlayer::Action_DeleteFile));
245
anItem->setIcon(stCMenuIcon("actionDiscard"));
246
247
+ const bool hasVideo = myPlugin->myVideo->hasVideoStream();
248
const StHandle< StArrayList<StString> >& anAudioStreams = myPlugin->myVideo->params.activeAudio->getList();
249
if(!anAudioStreams.isNull()
250
&& !anAudioStreams->isEmpty()) {
251
anItem = aMenu->addItem(tr(MENU_AUDIO));
252
anItem->setIcon(stCMenuIcon("actionStreamAudio"));
253
anItem->signals.onItemClick += stSlot(this, &StMoviePlayerGUI::doAudioStreamsCombo);
254
+ } else if(hasVideo) {
255
+ anItem = aMenu->addItem(tr(MENU_AUDIO));
256
+ anItem->setIcon(stCMenuIcon("actionStreamAudio"));
257
+ //anItem->signals.onItemClick += stSlot(myPlugin, &StMoviePlayer::doAddAudioStream);
258
+ anItem->signals.onItemClick += stSlot(this, &StMoviePlayerGUI::doAudioStreamsCombo);
259
}
260
261
const StHandle< StArrayList<StString> >& aSubsStreams = myPlugin->myVideo->params.activeSubtitles->getList();
262
263
anItem = aMenu->addItem(tr(MENU_SUBTITLES));
264
anItem->setIcon(stCMenuIcon("actionStreamSubtitles"));
265
anItem->signals.onItemClick += stSlot(this, &StMoviePlayerGUI::doSubtitlesStreamsCombo);
266
+ } else if(myPlugin->myVideo->hasAudioStream()
267
+ || hasVideo) {
268
+ anItem = aMenu->addItem(tr(MENU_SUBTITLES));
269
+ anItem->setIcon(stCMenuIcon("actionStreamSubtitles"));
270
+ //anItem->signals.onItemClick += stSlot(myPlugin, &StMoviePlayer::doAddSubtitleStream);
271
+ anItem->signals.onItemClick += stSlot(this, &StMoviePlayerGUI::doSubtitlesStreamsCombo);
272
}
273
274
- if(myPlugin->myVideo->hasVideoStream()) {
275
+ if(hasVideo) {
276
anItem = aMenu->addItem(tr(MENU_VIEW_DISPLAY_RATIO));
277
anItem->setIcon(stCMenuIcon("actionDisplayRatio"));
278
anItem->signals.onItemClick += stSlot(this, &StMoviePlayerGUI::doDisplayRatioCombo);
279
280
myPlugin->params.ToShowFps->signals.onChanged.connect(this, &StMoviePlayerGUI::doShowFPS);
281
282
myImage = new StGLImageRegion(this, theTextureQueue, false);
283
- myImage->setDragDelayMs(500.0);
284
+ myImage->changeIconPrev()->setTexturePath(iconTexture(stCString("actionBack"), scaleIcon(64)));
285
+ myImage->changeIconPrev()->setDrawShadow(true);
286
+ myImage->changeIconNext()->setTexturePath(iconTexture(stCString("actionNext"), scaleIcon(64)));
287
+ myImage->changeIconNext()->setDrawShadow(true);
288
+ myImage->signals.onOpenItem = stSlot(myPlugin, &StMoviePlayer::doFileNext);
289
+ myImage->setPlayList(thePlayList);
290
+ //myImage->setDragDelayMs(500.0);
291
myImage->params.DisplayMode->setName(tr(MENU_VIEW_DISPLAY_MODE));
292
myImage->params.DisplayMode->changeValues()[StGLImageRegion::MODE_STEREO] = tr(MENU_VIEW_DISPLAY_MODE_STEREO);
293
myImage->params.DisplayMode->changeValues()[StGLImageRegion::MODE_ONLY_LEFT] = tr(MENU_VIEW_DISPLAY_MODE_LEFT);
294
295
myImage->params.DisplayMode->changeValues()[StGLImageRegion::MODE_PARALLEL] = tr(MENU_VIEW_DISPLAY_MODE_PARALLEL);
296
myImage->params.DisplayMode->changeValues()[StGLImageRegion::MODE_CROSSYED] = tr(MENU_VIEW_DISPLAY_MODE_CROSSYED);
297
myImage->params.ToHealAnamorphicRatio->setValue(true);
298
+ myImage->params.ViewMode->signals.onChanged += stSlot(myPlugin, &StMoviePlayer::doSwitchViewMode);
299
300
mySubtitles = new StGLSubtitles (myImage, theSubQueue,
301
myPlugin->params.SubtitlesPlace,
302
- myPlugin->params.SubtitlesTopDY,
303
- myPlugin->params.SubtitlesBottomDY,
304
- myPlugin->params.SubtitlesSize,
305
- myPlugin->params.SubtitlesParallax,
306
- myPlugin->params.SubtitlesParser);
307
+ myPlugin->params.SubtitlesSize);
308
+ mySubtitles->params.TopDY = myPlugin->params.SubtitlesTopDY;
309
+ mySubtitles->params.BottomDY = myPlugin->params.SubtitlesBottomDY;
310
+ mySubtitles->params.Parallax = myPlugin->params.SubtitlesParallax;
311
+ mySubtitles->params.Parser = myPlugin->params.SubtitlesParser;
312
+ mySubtitles->params.ToApplyStereo = myPlugin->params.SubtitlesApplyStereo;
313
314
if(myPlugin->params.ToShowFps->getValue()) {
315
myFpsWidget = new StGLFpsLabel(this);
316
317
float theAspect) {
318
const int aNewSizeX = theViewPort.width();
319
const int aNewSizeY = theViewPort.height();
320
+ int aGapTopX = 0, aGapTopY = 0, aGapBotX = 0, aGapBotY = 0;
321
+ if(isMobile()) {
322
+ // add gap for hidden system navigation buttons
323
+ static const int THE_NAVIGATION_GAPX = 32;
324
+ static const int THE_NAVIGATION_GAPY = 16;
325
+ if(theAspect < 9.0 / 16.0 && theAspect > 0.0) {
326
+ aGapTopY = aGapBotY = stMax(0, scale(stMin(THE_NAVIGATION_GAPY, int((1.0 / theAspect * 360) - 360 * 2))));
327
+ } else if(theAspect > 9.0 / 16.0) {
328
+ aGapTopX = aGapBotX = stMax(0, scale(stMin(THE_NAVIGATION_GAPX, int((theAspect * 360) - 360 * 2))));
329
+ }
330
+ } else {
331
+ aGapTopY = scale(DISPL_Y_REGION_UPPER);
332
+ aGapTopX = scale(DISPL_X_REGION_UPPER);
333
+ aGapBotX = scale(DISPL_X_REGION_BOTTOM);
334
+ }
335
336
// image should fit entire view
337
myImage->changeRectPx().top() = -theMargins.top;
338
339
myImage->changeRectPx().right() = -theMargins.left + aNewSizeX;
340
341
if(myPanelUpper != NULL) {
342
- myPanelUpper->changeRectPx().right() = stMax(aNewSizeX - theMargins.right - theMargins.left, 2);
343
+ myPanelUpper->changeRectPx().top() = aGapTopY;
344
+ myPanelUpper->changeRectPx().left() = aGapTopX;
345
+ myPanelUpper->changeRectPx().right() = aGapTopX + stMax(aNewSizeX - theMargins.right - theMargins.left - 2 * aGapTopX, 2);
346
}
347
if(myPanelBottom != NULL) {
348
- const int aGapX = myPanelBottom->changeRectPx().left();
349
- myPanelBottom->changeRectPx().right() = aGapX + stMax(aNewSizeX - theMargins.right - theMargins.left - 2 * aGapX, 2);
350
+ myPanelBottom->changeRectPx().top() = -aGapBotY;
351
+ myPanelBottom->changeRectPx().left() = aGapBotX;
352
+ myPanelBottom->changeRectPx().right() = aGapBotX + stMax(aNewSizeX - theMargins.right - theMargins.left - 2 * aGapBotX, 2);
353
}
354
355
stglResizeSeekBar();
356
357
void StMoviePlayerGUI::stglResizeSeekBar() {
358
if(mySeekBar != NULL
359
&& myPanelBottom != NULL) {
360
- const int aPanelSizeY = myPanelBottom->getRectPx().height();
361
+ const int aPanelSizeY = myPanelBottom->getRectPx().top() + myPanelBottom->getRectPx().height();
362
const int aPanelSizeX = myPanelBottom->getRectPx().width();
363
const int aSeekSizeY = mySeekBar->getRectPx().height();
364
const int aBoxWidth = myTimeBox->getRectPx().width();
365
366
367
}
368
369
-void StMoviePlayerGUI::setVisibility(const StPointD_t& theCursor) {
370
+void StMoviePlayerGUI::doGesture(const StGestureEvent& theEvent) {
371
+ if(myImage == NULL) {
372
+ return;
373
+ }
374
+
375
+ if(theEvent.Type == stEvent_Gesture1Tap) {
376
+ myTapTimer.restart();
377
+ } else if(theEvent.Type == stEvent_Gesture1DoubleTap) {
378
+ myTapTimer.stop();
379
+ }
380
+
381
+ for(StGLWidget *aChildIter(getChildren()->getLast()), *aChildActive(NULL); aChildIter != NULL;) {
382
+ aChildActive = aChildIter;
383
+ aChildIter = aChildIter->getPrev();
384
+ if(aChildActive->isVisibleAndPointIn(getCursorZo())) {
385
+ if(aChildActive == myImage) {
386
+ myImage->doGesture(theEvent);
387
+ }
388
+ return;
389
+ }
390
+ }
391
+}
392
+
393
+void StMoviePlayerGUI::setVisibility(const StPointD_t& theCursor,
394
+ bool theToForceHide,
395
+ bool theToForceShow) {
396
const bool toShowAdjust = myPlugin->params.ToShowAdjustImage->getValue();
397
const bool toShowPlayList = myPlugin->params.ToShowPlayList->getValue();
398
const bool hasMainMenu = myPlugin->params.ToShowMenu->getValue()
399
&& myMenuRoot != NULL;
400
const bool hasUpperPanel = myPlugin->params.ToShowTopbar->getValue()
401
&& myPanelUpper != NULL;
402
+ const bool hasBottomPanel = myPlugin->params.ToShowBottom->getValue()
403
+ && (myPanelBottom != NULL || mySeekBar != NULL);
404
405
const int aRootSizeY = getRectPx().height();
406
const bool hasVideo = myPlugin->myVideo->hasVideoStream();
407
+ if(!hasVideo && !myTapTimer.isOn()
408
+ && !myPlugin->myPlayList->isEmpty()) {
409
+ myEmptyTimer.restart();
410
+ } else {
411
+ myEmptyTimer.stop();
412
+ }
413
+ if(myEmptyTimer.getElapsedTime() >= 2.5) {
414
+ myVisibilityTimer.restart();
415
+ myEmptyTimer.stop();
416
+ }
417
+ if(myTapTimer.getElapsedTime() >= 0.5) {
418
+ myVisibilityTimer.restart();
419
+ myTapTimer.stop();
420
+ }
421
+ if(theToForceShow) {
422
+ myVisibilityTimer.restart();
423
+ } else if(theToForceHide) {
424
+ myVisibilityTimer.restart(THE_VISIBILITY_IDLE_TIME + 0.001);
425
+ }
426
const bool isMouseActive = myWindow->isMouseMoved();
427
const double aStillTime = myVisibilityTimer.getElapsedTime();
428
429
430
&& aSrcFormat != StFormat_Mono
431
&& aSrcFormat != StFormat_AUTO;
432
433
- myIsVisibleGUI = !hasVideo
434
- || isMouseActive
435
+ myIsVisibleGUI = isMouseActive
436
|| aParams.isNull()
437
- || aStillTime < 2.0
438
+ || aStillTime < THE_VISIBILITY_IDLE_TIME
439
|| (hasUpperPanel && myPanelUpper->isPointIn(theCursor))
440
- || (myPanelBottom != NULL && int(aRootSizeY * theCursor.y()) > (aRootSizeY - 2 * myPanelBottom->getRectPx().height())
441
- && theCursor.y() < 1.0)
442
- || (mySeekBar != NULL && mySeekBar ->isPointIn(theCursor))
443
- || (myPlayList != NULL && toShowPlayList && myPlayList->isPointIn(theCursor))
444
+ || (hasBottomPanel && myPanelBottom != NULL
445
+ && int(aRootSizeY * theCursor.y()) > (aRootSizeY - 2 * myPanelBottom->getRectPx().height())
446
+ && theCursor.y() < 1.0)
447
+ || (hasBottomPanel && mySeekBar != NULL && mySeekBar->isPointIn(theCursor))
448
+ || (hasBottomPanel && myPlayList != NULL && toShowPlayList && myPlayList->isPointIn(theCursor))
449
|| (hasMainMenu && myMenuRoot->isActive());
450
if(!myIsVisibleGUI
451
&& myBtnPlay != NULL
452
453
|| theCursor.y() < 0.0 || theCursor.y() > 1.0)) {
454
myIsVisibleGUI = true;
455
}
456
- const float anOpacity = (float )myVisLerp.perform(myIsVisibleGUI, false);
457
+ const float anOpacity = (float )myVisLerp.perform(myIsVisibleGUI, theToForceHide || theToForceShow);
458
if(isMouseActive) {
459
myVisibilityTimer.restart();
460
}
461
462
myPanelUpper->setOpacity(hasUpperPanel ? anOpacity : 0.0f, true);
463
}
464
if(mySeekBar != NULL) {
465
- mySeekBar->setOpacity(anOpacity, false);
466
+ mySeekBar->setOpacity(hasBottomPanel ? anOpacity : 0.0f, false);
467
}
468
if(myPanelBottom != NULL) {
469
- myPanelBottom->setOpacity(anOpacity, true);
470
+ myPanelBottom->setOpacity(hasBottomPanel ? anOpacity : 0.0f, true);
471
}
472
473
if(myAdjustOverlay != NULL
474
475
}
476
if(myPlayList != NULL
477
&& toShowPlayList) {
478
- myPlayList->setOpacity(anOpacity, true);
479
+ myPlayList->setOpacity(hasBottomPanel ? anOpacity : 0.0f, true);
480
}
481
482
const StPlayList::CurrentPosition aCurrPos = myPlugin->myPlayList->getCurrentPosition();
483
484
if(!toShowPano
485
&& hasVideo
486
&& !aParams.isNull()
487
- && st::probePanorama(aParams->StereoFormat,
488
+ /*&& st::probePanorama(aParams->StereoFormat,
489
aParams->Src1SizeX, aParams->Src1SizeY,
490
- aParams->Src2SizeX, aParams->Src2SizeY) != StPanorama_OFF) {
491
+ aParams->Src2SizeX, aParams->Src2SizeY) != StPanorama_OFF*/) {
492
toShowPano = true;
493
}
494
if(myBtnPanorama != NULL) {
495
496
} else if(::isPointIn(myBtnPanorama, theCursor)) {
497
size_t aTrPano = MENU_VIEW_SURFACE_PLANE;
498
switch(aViewMode) {
499
- case StViewSurface_Plain: aTrPano = MENU_VIEW_SURFACE_PLANE; break;
500
- case StViewSurface_Sphere: aTrPano = MENU_VIEW_SURFACE_SPHERE; break;
501
- case StViewSurface_Cubemap: aTrPano = MENU_VIEW_SURFACE_CUBEMAP; break;
502
+ case StViewSurface_Plain: aTrPano = MENU_VIEW_SURFACE_PLANE; break;
503
+ case StViewSurface_Theater: aTrPano = MENU_VIEW_SURFACE_THEATER; break;
504
+ case StViewSurface_Sphere: aTrPano = MENU_VIEW_SURFACE_SPHERE; break;
505
+ case StViewSurface_Hemisphere: aTrPano = MENU_VIEW_SURFACE_HEMISPHERE; break;
506
+ case StViewSurface_Cubemap: aTrPano = MENU_VIEW_SURFACE_CUBEMAP; break;
507
+ case StViewSurface_CubemapEAC: aTrPano = MENU_VIEW_SURFACE_CUBEMAP_EAC; break;
508
+ case StViewSurface_Cylinder: aTrPano = MENU_VIEW_SURFACE_CYLINDER; break;
509
}
510
myDescr->setText(tr(MENU_VIEW_PANORAMA) + "\n" + tr(aTrPano));
511
} else if(::isPointIn(myBtnAdjust, theCursor)) {
512
513
aBuilder.getMenu()->addItem(myPlugin->params.ToForceBFormat);
514
}
515
}
516
- if(myWindow->isMobile()) {
517
- aBuilder.display();
518
- return;
519
- }
520
521
//aBuilder.getMenu()->addSplitter();
522
StGLMenuItem* aDelayItem = NULL;
523
524
aBuilder.display();
525
}
526
527
+void StMoviePlayerGUI::doSubtitlesPlacement(const size_t ) {
528
+ StGLMenu* aMenu = new StGLMenu(this, 0, 0, StGLMenu::MENU_VERTICAL, true);
529
+ aMenu->setCorner(StGLCorner(ST_VCORNER_BOTTOM, ST_HCORNER_RIGHT));
530
+ aMenu->setContextual(true);
531
+ fillSubtitlesFontSize(aMenu);
532
+ fillSubtitlesPlacement(aMenu);
533
+ aMenu->stglInit();
534
+ setFocus(aMenu);
535
+}
536
+
537
+void StMoviePlayerGUI::fillSubtitlesFontSize(StGLMenu* theMenu) {
538
+ StGLMenuItem* anItem = theMenu->addItem(tr(MENU_SUBTITLES_SIZE));
539
+ anItem->setIcon(stCMenuIcon("actionFontSize"), false);
540
+ anItem->changeMargins().right = scale(100 + 16);
541
+ StGLRangeFieldFloat32* aRange = new StGLRangeFieldFloat32(anItem, myPlugin->params.SubtitlesSize,
542
+ -scale(16), 0, StGLCorner(ST_VCORNER_CENTER, ST_HCORNER_RIGHT));
543
+ aRange->changeRectPx().bottom() = aRange->getRectPx().top() + theMenu->getItemHeight();
544
+ aRange->setFormat(stCString("%02.0f"));
545
+ aRange->setColor(StGLRangeFieldFloat32::FieldColor_Default, aBlack);
546
+ aRange->setColor(StGLRangeFieldFloat32::FieldColor_Positive, aBlack);
547
+ aRange->setColor(StGLRangeFieldFloat32::FieldColor_Negative, aBlack);
548
+}
549
+
550
+void StMoviePlayerGUI::fillSubtitlesPlacement(StGLMenu* theMenu) {
551
+ StGLMenuItem* anItem = theMenu->addItem(tr(MENU_SUBTITLES_TOP), myPlugin->params.SubtitlesPlace, ST_VCORNER_TOP);
552
+ anItem->changeMargins().right = scale(100 + 16);
553
+ StGLRangeFieldFloat32* aRange = new StGLRangeFieldFloat32(anItem, myPlugin->params.SubtitlesTopDY,
554
+ -scale(16), 0, StGLCorner(ST_VCORNER_CENTER, ST_HCORNER_RIGHT));
555
+ aRange->changeRectPx().bottom() = aRange->getRectPx().top() + theMenu->getItemHeight();
556
+ aRange->setFormat(stCString("%+03.0f"));
557
+ aRange->setColor(StGLRangeFieldFloat32::FieldColor_Default, aBlack);
558
+ aRange->setColor(StGLRangeFieldFloat32::FieldColor_Positive, aGreen);
559
+ aRange->setColor(StGLRangeFieldFloat32::FieldColor_Negative, aRed);
560
+
561
+ anItem = theMenu->addItem(tr(MENU_SUBTITLES_BOTTOM), myPlugin->params.SubtitlesPlace, ST_VCORNER_BOTTOM);
562
+ anItem->changeMargins().right = scale(100 + 16);
563
+ aRange = new StGLRangeFieldFloat32(anItem, myPlugin->params.SubtitlesBottomDY,
564
+ -scale(16), 0, StGLCorner(ST_VCORNER_CENTER, ST_HCORNER_RIGHT));
565
+ aRange->changeRectPx().bottom() = aRange->getRectPx().top() + theMenu->getItemHeight();
566
+ aRange->setFormat(stCString("%+03.0f"));
567
+ aRange->setColor(StGLRangeFieldFloat32::FieldColor_Default, aBlack);
568
+ aRange->setColor(StGLRangeFieldFloat32::FieldColor_Positive, aGreen);
569
+ aRange->setColor(StGLRangeFieldFloat32::FieldColor_Negative, aRed);
570
+
571
+ anItem = theMenu->addItem(tr(MENU_SUBTITLES_PARALLAX));
572
+ anItem->changeMargins().right = scale(100 + 16);
573
+ aRange = new StGLRangeFieldFloat32(anItem, myPlugin->params.SubtitlesParallax,
574
+ -scale(16), 0, StGLCorner(ST_VCORNER_CENTER, ST_HCORNER_RIGHT));
575
+ aRange->changeRectPx().bottom() = aRange->getRectPx().top() + theMenu->getItemHeight();
576
+ aRange->setFormat(stCString("%+03.0f"));
577
+ aRange->setColor(StGLRangeFieldFloat32::FieldColor_Default, aBlack);
578
+ aRange->setColor(StGLRangeFieldFloat32::FieldColor_Positive, aBlack);
579
+ aRange->setColor(StGLRangeFieldFloat32::FieldColor_Negative, aBlack);
580
+}
581
+
582
void StMoviePlayerGUI::doSubtitlesStreamsCombo(const size_t ) {
583
const StHandle< StArrayList<StString> >& aStreams = myPlugin->myVideo->params.activeSubtitles->getList();
584
+ const bool hasAudioStream = myPlugin->myVideo->hasAudioStream();
585
+ const bool hasVideoStream = myPlugin->myVideo->hasVideoStream();
586
587
StGLCombobox::ListBuilder aBuilder(this);
588
589
590
aBuilder.getMenu()->addItem(aStreams->getValue(aStreamId), myPlugin->params.SubtitlesStream, int32_t(aStreamId));
591
}
592
}
593
- if(myWindow->isMobile()) {
594
- aBuilder.display();
595
- return;
596
- }
597
598
if(!aStreams.isNull()
599
&& !aStreams->isEmpty()) {
600
//myMenuSubtitles->addSplitter();
601
- StGLMenuItem* anItem = aBuilder.getMenu()->addItem(tr(MENU_SUBTITLES_SIZE));
602
- anItem->setIcon(stCMenuIcon("actionFontSize"), false);
603
- anItem->changeMargins().right = scale(100 + 16);
604
- StGLRangeFieldFloat32* aRange = new StGLRangeFieldFloat32(anItem, myPlugin->params.SubtitlesSize,
605
- -scale(16), 0, StGLCorner(ST_VCORNER_CENTER, ST_HCORNER_RIGHT));
606
- aRange->changeRectPx().bottom() = aRange->getRectPx().top() + aBuilder.getMenu()->getItemHeight();
607
- aRange->setFormat(stCString("%02.0f"));
608
- aRange->setColor(StGLRangeFieldFloat32::FieldColor_Default, aBlack);
609
- aRange->setColor(StGLRangeFieldFloat32::FieldColor_Positive, aBlack);
610
- aRange->setColor(StGLRangeFieldFloat32::FieldColor_Negative, aBlack);
611
+ if(!myWindow->isMobile()) {
612
+ fillSubtitlesFontSize(aBuilder.getMenu());
613
+ }
614
615
StGLMenu* aPlaceMenu = new StGLMenu(this, 0, 0, StGLMenu::MENU_VERTICAL);
616
+ fillSubtitlesPlacement(aPlaceMenu);
617
+ aBuilder.getMenu()->addItem(tr(MENU_SUBTITLES_PLACEMENT), aPlaceMenu)
618
+ ->signals.onItemClick.connect(this, &StMoviePlayerGUI::doSubtitlesPlacement);
619
+ }
620
621
- anItem = aPlaceMenu->addItem(tr(MENU_SUBTITLES_TOP), myPlugin->params.SubtitlesPlace, ST_VCORNER_TOP);
622
- anItem->changeMargins().right = scale(100 + 16);
623
- aRange = new StGLRangeFieldFloat32(anItem, myPlugin->params.SubtitlesTopDY,
624
- -scale(16), 0, StGLCorner(ST_VCORNER_CENTER, ST_HCORNER_RIGHT));
625
- aRange->changeRectPx().bottom() = aRange->getRectPx().top() + aBuilder.getMenu()->getItemHeight();
626
- aRange->setFormat(stCString("%+03.0f"));
627
- aRange->setColor(StGLRangeFieldFloat32::FieldColor_Default, aBlack);
628
- aRange->setColor(StGLRangeFieldFloat32::FieldColor_Positive, aGreen);
629
- aRange->setColor(StGLRangeFieldFloat32::FieldColor_Negative, aRed);
630
-
631
- anItem = aPlaceMenu->addItem(tr(MENU_SUBTITLES_BOTTOM), myPlugin->params.SubtitlesPlace, ST_VCORNER_BOTTOM);
632
- anItem->changeMargins().right = scale(100 + 16);
633
- aRange = new StGLRangeFieldFloat32(anItem, myPlugin->params.SubtitlesBottomDY,
634
- -scale(16), 0, StGLCorner(ST_VCORNER_CENTER, ST_HCORNER_RIGHT));
635
- aRange->changeRectPx().bottom() = aRange->getRectPx().top() + aBuilder.getMenu()->getItemHeight();
636
- aRange->setFormat(stCString("%+03.0f"));
637
- aRange->setColor(StGLRangeFieldFloat32::FieldColor_Default, aBlack);
638
- aRange->setColor(StGLRangeFieldFloat32::FieldColor_Positive, aGreen);
639
- aRange->setColor(StGLRangeFieldFloat32::FieldColor_Negative, aRed);
640
-
641
- anItem = aPlaceMenu->addItem(tr(MENU_SUBTITLES_PARALLAX));
642
- anItem->changeMargins().right = scale(100 + 16);
643
- aRange = new StGLRangeFieldFloat32(anItem, myPlugin->params.SubtitlesParallax,
644
- -scale(16), 0, StGLCorner(ST_VCORNER_CENTER, ST_HCORNER_RIGHT));
645
- aRange->changeRectPx().bottom() = aRange->getRectPx().top() + aBuilder.getMenu()->getItemHeight();
646
- aRange->setFormat(stCString("%+03.0f"));
647
- aRange->setColor(StGLRangeFieldFloat32::FieldColor_Default, aBlack);
648
- aRange->setColor(StGLRangeFieldFloat32::FieldColor_Positive, aBlack);
649
- aRange->setColor(StGLRangeFieldFloat32::FieldColor_Negative, aBlack);
650
-
651
- anItem = aBuilder.getMenu()->addItem(tr(MENU_SUBTITLES_PLACEMENT), aPlaceMenu);
652
- }
653
-
654
- aBuilder.getMenu()->addItem(tr(MENU_SUBTITLES_PARSER), aParserMenu)
655
- ->setIcon(stCMenuIcon("actionTextFormat"), false);
656
- if(myPlugin->myVideo->hasAudioStream()
657
- || myPlugin->myVideo->hasVideoStream()) {
658
+ if(!aStreams.isNull()
659
+ && !aStreams->isEmpty()
660
+ && hasVideoStream) {
661
+ StHandle<StStereoParams> aParams = myImage->getSource();
662
+ StFormat aSrcFormat = (StFormat )myPlugin->params.SrcStereoFormat->getValue();
663
+ if(aSrcFormat == StFormat_AUTO && !aParams.isNull()) {
664
+ aSrcFormat = aParams->StereoFormat;
665
+ }
666
+ if(aSrcFormat == StFormat_SideBySide_LR
667
+ || aSrcFormat == StFormat_SideBySide_RL
668
+ || aSrcFormat == StFormat_TopBottom_LR
669
+ || aSrcFormat == StFormat_TopBottom_RL) {
670
+ aBuilder.getMenu()->addItem(tr(MENU_SUBTITLES_STEREO), myPlugin->params.SubtitlesApplyStereo);
671
+ }
672
+ }
673
+ if(!myWindow->isMobile()) {
674
+ aBuilder.getMenu()->addItem(tr(MENU_SUBTITLES_PARSER), aParserMenu)
675
+ ->setIcon(stCMenuIcon("actionTextFormat"), false);
676
+ }
677
+ if(hasAudioStream || hasVideoStream) {
678
//aBuilder.getMenu()->addSplitter();
679
aBuilder.getMenu()->addItem(tr(MENU_SUBTITLES_ATTACH))
680
->setIcon(stCMenuIcon("actionOpen"), false)
681
682
aParams.add(myPlugin->StApplication::params.ActiveDevice);
683
aParams.add(myImage->params.DisplayMode);
684
aParams.add(myPlugin->params.ToStickPanorama);
685
+ aParams.add(myPlugin->params.ToSwapJPS);
686
aRend->getOptions(aParams);
687
aParams.add(myPlugin->params.ToShowFps);
688
aParams.add(myPlugin->params.UseGpu);
689
690
}
691
692
aParams.add(myLangMap->params.language);
693
+ aParams.add(myPlugin->params.ToMixImagesVideos);
694
+ aParams.add(myPlugin->params.SlideShowDelay);
695
aParams.add(myPlugin->params.IsMobileUI);
696
+#if defined(_WIN32) || defined(__APPLE__) // implemented only on Windows and macOS
697
+ aParams.add(myPlugin->params.IsExclusiveFullScreen);
698
+#endif
699
+ aParams.add(myPlugin->params.ToSmoothUploads);
700
if(isMobile()) {
701
//aParams.add(myPlugin->params.ToHideStatusBar);
702
aParams.add(myPlugin->params.ToHideNavBar);
703
704
aParams.add(myPlugin->params.BlockSleeping);
705
aParams.add(myPlugin->params.ToOpenLast);
706
}
707
-#if !defined(ST_NO_UPDATES_CHECK)
708
+#if defined(ST_UPDATES_CHECK)
709
aParams.add(myPlugin->params.CheckUpdatesDays);
710
#endif
711
712
+ if(!myWindow->isMobile()) {
713
+ StHandle<StBoolParamNamed> aDefDrawerParam = myPlugin->createDefaultDrawerParam(stCString("StMoviePlayer"),
714
+ stCString("sView launcher starts Movie Player"));
715
+ aParams.add(aDefDrawerParam);
716
+ }
717
+
718
StInfoDialog* aDialog = new StInfoDialog(myPlugin, this, tr(MENU_HELP_SETTINGS), scale(768), scale(300));
719
720
const int aWidthMax = aDialog->getContent()->getRectPx().width();
721
sview-17_04.tar.gz/StMoviePlayer/StMoviePlayerGUI.h -> sview-20_08.tar.gz/StMoviePlayer/StMoviePlayerGUI.h
Changed
56
1
2
/**
3
- * Copyright © 2009-2017 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2009-2020 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* StMoviePlayer program is free software: you can redistribute it and/or modify
7
* it under the terms of the GNU General Public License as published by
8
9
ST_LOCAL virtual void stglUpdate(const StPointD_t& thePointZo,
10
bool theIsPreciseInput) ST_ATTR_OVERRIDE;
11
12
- ST_LOCAL void setVisibility(const StPointD_t& theCursor);
13
+ /**
14
+ * Handle gesture.
15
+ */
16
+ ST_LOCAL void doGesture(const StGestureEvent& theEvent);
17
+ ST_LOCAL bool isVisibleGUI() const { return myVisLerp.getValue() > 0.0; }
18
+ ST_LOCAL void setVisibility(const StPointD_t& theCursor,
19
+ bool theToForceHide = false,
20
+ bool theToForceShow = false);
21
22
public:
23
24
25
ST_LOCAL void fillDisplayRatioMenu(StGLMenu* theMenu);
26
ST_LOCAL void fillSrcFormatMenu(StGLMenu* theMenu);
27
ST_LOCAL void fillPanoramaMenu (StGLMenu* theMenu);
28
+ ST_LOCAL void fillSubtitlesFontSize(StGLMenu* theMenu);
29
+ ST_LOCAL void fillSubtitlesPlacement(StGLMenu* theMenu);
30
31
private: //! @name mobile interface creation routines
32
33
34
ST_LOCAL void doChangeHotKey1(const size_t );
35
ST_LOCAL void doChangeHotKey2(const size_t );
36
37
- ST_LOCAL void doOpenFile(const size_t );
38
+ ST_LOCAL void doOpenFile(const size_t theFileType);
39
ST_LOCAL void doShowMobileExMenu(const size_t );
40
ST_LOCAL void doMobileSettings(const size_t );
41
ST_LOCAL void doAudioStreamsCombo(const size_t );
42
ST_LOCAL void doSubtitlesStreamsCombo(const size_t );
43
+ ST_LOCAL void doSubtitlesPlacement(const size_t );
44
ST_LOCAL void doDisplayRatioCombo(const size_t );
45
ST_LOCAL void doDisplayStereoFormatCombo(const size_t );
46
ST_LOCAL void doPanoramaCombo(const size_t );
47
48
StWindow* myWindow; //!< link to the window instance
49
StTranslations* myLangMap; //!< translated strings map
50
StTimer myVisibilityTimer; //!< minimum visible delay
51
+ StTimer myEmptyTimer; //!< empty list delay
52
+ StTimer myTapTimer; //!< single tap delay
53
StGLAnimationLerp myVisLerp;
54
55
StGLImageRegion* myImage; //!< the main video frame
56
sview-17_04.tar.gz/StMoviePlayer/StMoviePlayerInfo.h -> sview-20_08.tar.gz/StMoviePlayer/StMoviePlayerInfo.h
Changed
32
1
2
#define ST_M4A_MIME_STRING ST_M4A_MIME ":" ST_M4A_EXT ":" ST_M4A_DESC
3
4
/**
5
+ *.insv - Insta360 Video (mp4 unstitched panorama)
6
+ */
7
+#define ST_INSV_MIME "video/x-insv"
8
+#define ST_INSV_DESC "Insta360 Video"
9
+#define ST_INSV_EXT "insv"
10
+#define ST_INSV_MIME_STRING ST_INSV_MIME ":" ST_INSV_EXT ":" ST_INSV_DESC
11
+
12
+/**
13
*.mov;*.qt - QuickTime Video (Apple)
14
*/
15
#define ST_MOV_MIME "video/quicktime"
16
17
ST_M4V_MIME_STRING ";" \
18
ST_MP4V_MIME_STRING ";" \
19
ST_M4A_MIME_STRING ";" \
20
+ST_INSV_MIME_STRING ";" \
21
ST_MOV_MIME_STRING ";" \
22
ST_QT_MIME_STRING ";" \
23
ST_FLV_MIME_STRING ";" \
24
25
ST_APE_MIME_STRING ";" \
26
ST_AOB_MIME_STRING ";" \
27
ST_MP3_MIME_STRING ";" \
28
+ST_M4A_MIME_STRING ";" \
29
ST_AAC_MIME_STRING ";" \
30
ST_OGG_MIME_STRING ";" \
31
ST_OPUS_MIME_STRING ";" \
32
sview-17_04.tar.gz/StMoviePlayer/StMoviePlayerStrings.cpp -> sview-20_08.tar.gz/StMoviePlayer/StMoviePlayerStrings.cpp
Changed
88
1
2
/**
3
- * Copyright © 2013-2017 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2013-2020 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* StMoviePlayer program is free software: you can redistribute it and/or modify
7
* it under the terms of the GNU General Public License as published by
8
9
"Top");
10
theStrings(MENU_SUBTITLES_BOTTOM,
11
"Bottom");
12
+ theStrings(MENU_SUBTITLES_STEREO,
13
+ "Apply stereo format");
14
theStrings(MENU_SUBTITLES_PLAIN_TEXT,
15
"Plain text");
16
theStrings(MENU_SUBTITLES_LITE_HTML,
17
18
"Plane");
19
theStrings(MENU_VIEW_SURFACE_SPHERE,
20
"Sphere");
21
+ theStrings(MENU_VIEW_SURFACE_HEMISPHERE,
22
+ "Hemisphere");
23
theStrings(MENU_VIEW_SURFACE_CYLINDER,
24
"Cylinder");
25
theStrings(MENU_VIEW_SURFACE_CUBEMAP,
26
"Cubemap");
27
+ theStrings(MENU_VIEW_SURFACE_THEATER,
28
+ "Theater");
29
+ theStrings(MENU_VIEW_SURFACE_CUBEMAP_EAC,
30
+ "Equiangular cubemap");
31
theStrings(MENU_VIEW_TRACK_HEAD,
32
"Track orientation");
33
theStrings(MENU_VIEW_TRACK_HEAD_POOR,
34
35
"Nearest");
36
theStrings(MENU_VIEW_TEXFILTER_LINEAR,
37
"Linear");
38
+ theStrings(MENU_VIEW_TEXFILTER_TRILINEAR,
39
+ "Trilinear");
40
theStrings(MENU_VIEW_TEXFILTER_BLEND,
41
"Blend Deinterlace");
42
theStrings(MENU_CHANGE_DEVICE,
43
44
"About Plugin...");
45
theStrings(MENU_FPS,
46
"FPS Control");
47
+ theStrings(MENU_EXCLUSIVE_FULLSCREEN,
48
+ "Exclusive Fullscreen mode");
49
theStrings(MENU_FPS_VSYNC,
50
"VSync");
51
theStrings(MENU_FPS_METER,
52
53
"Hide system navigation bar");
54
theStrings(OPTION_OPEN_LAST_ON_STARTUP,
55
"Open last played file on startup");
56
+ theStrings(OPTION_SWAP_JPS,
57
+ "Swap JPS/PNS views order");
58
59
theStrings(FILE_VIDEO_OPEN,
60
"Open another movie");
61
62
"Choose the video file to open");
63
theStrings(DIALOG_OPEN_RIGHT,
64
"Choose RIGHT video file to open");
65
+ theStrings(DIALOG_OPEN_AUDIO,
66
+ "Choose audio file to attach");
67
+ theStrings(DIALOG_OPEN_SUBTITLES,
68
+ "Choose subtitles file to attach");
69
theStrings(DIALOG_FILE_INFO,
70
"File Info");
71
theStrings(DIALOG_FILE_NOINFO,
72
73
addAction(theStrings, StMoviePlayer::Action_PanoramaOnOff,
74
"DoPanoramaOnOff",
75
"Enable/disable panorama mode");
76
+ addAction(theStrings, StMoviePlayer::Action_ShowGUI,
77
+ "DoShowGUI",
78
+ "Show/hide GUI");
79
+
80
+ theStrings.addAlias("DoOutStereoNormal", MENU_VIEW_DISPLAY_MODE_STEREO);
81
+ theStrings.addAlias("DoOutStereoLeftView", MENU_VIEW_DISPLAY_MODE_LEFT);
82
+ theStrings.addAlias("DoOutStereoRightView", MENU_VIEW_DISPLAY_MODE_RIGHT);
83
+ theStrings.addAlias("DoOutStereoParallelPair", MENU_VIEW_DISPLAY_MODE_PARALLEL);
84
+ theStrings.addAlias("DoOutStereoCrossEyed", MENU_VIEW_DISPLAY_MODE_CROSSYED);
85
}
86
87
};
88
sview-17_04.tar.gz/StMoviePlayer/StMoviePlayerStrings.h -> sview-20_08.tar.gz/StMoviePlayer/StMoviePlayerStrings.h
Changed
63
1
2
/**
3
- * Copyright © 2009-2017 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2009-2020 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* StMoviePlayer program is free software: you can redistribute it and/or modify
7
* it under the terms of the GNU General Public License as published by
8
9
MENU_VIEW_TEXFILTER_NEAREST = 1260,
10
MENU_VIEW_TEXFILTER_LINEAR = 1261,
11
MENU_VIEW_TEXFILTER_BLEND = 1262,
12
+ MENU_VIEW_TEXFILTER_TRILINEAR = 1263,
13
14
MENU_VIEW_ADJUST_RESET = 1270,
15
MENU_VIEW_ADJUST_BRIGHTNESS = 1271,
16
17
MENU_VIEW_SURFACE_SPHERE = 1281,
18
MENU_VIEW_SURFACE_CYLINDER = 1282,
19
MENU_VIEW_SURFACE_CUBEMAP = 1283,
20
+ MENU_VIEW_SURFACE_HEMISPHERE= 1284,
21
MENU_VIEW_TRACK_HEAD = 1285,
22
MENU_VIEW_TRACK_HEAD_POOR = 1286,
23
MENU_VIEW_TRACK_HEAD_AUDIO = 1287,
24
MENU_VIEW_STICK_PANORAMA360 = 1288,
25
+ MENU_VIEW_SURFACE_CUBEMAP_EAC = 1293,
26
+ MENU_VIEW_SURFACE_THEATER = 1294,
27
28
// Root -> Audio menu
29
MENU_AUDIO = 1300,
30
31
MENU_SUBTITLES_PLACEMENT= 1357,
32
MENU_SUBTITLES_TOP = 1358,
33
MENU_SUBTITLES_BOTTOM = 1359,
34
+ MENU_SUBTITLES_STEREO = 1370,
35
36
MENU_SUBTITLES_PLAIN_TEXT = 1360,
37
MENU_SUBTITLES_LITE_HTML = 1361,
38
39
MENU_CHANGE_DEVICE = 1400, // Root -> Output -> Change Device menu
40
MENU_ABOUT_RENDERER = 1401,
41
MENU_FPS = 1402,
42
+ MENU_EXCLUSIVE_FULLSCREEN = 1404,
43
44
// Root -> Output -> FPS Control menu
45
MENU_FPS_VSYNC = 1420,
46
47
OPTION_EXIT_ON_ESCAPE_WINDOWED = 1705,
48
OPTION_HIDE_NAVIGATION_BAR = 1710,
49
OPTION_OPEN_LAST_ON_STARTUP = 1711,
50
+ OPTION_SWAP_JPS = 1712,
51
52
// Open/Save dialogs
53
DIALOG_OPEN_FILE = 2000,
54
55
DIALOG_DELETE_FILE_TITLE = 2005,
56
DIALOG_DELETE_FILE_QUESTION = 2006,
57
DIALOG_FILE_DECODERS = 2007,
58
+ DIALOG_OPEN_AUDIO = 2008,
59
+ DIALOG_OPEN_SUBTITLES = 2009,
60
61
DIALOG_SAVE_SNAPSHOT = 2010,
62
DIALOG_NOTHING_TO_SAVE = 2011,
63
sview-17_04.tar.gz/StMoviePlayer/StVideo/StAVPacketQueue.cpp -> sview-20_08.tar.gz/StMoviePlayer/StVideo/StAVPacketQueue.cpp
Changed
97
1
2
myCodecCtx(NULL),
3
myCodec(NULL),
4
myCodecAuto(NULL),
5
+ myCodecAutoId(AV_CODEC_ID_NONE),
6
myGetFrmtInit(NULL),
7
myGetBuffInit(NULL),
8
myPtsStartBase(0.0),
9
10
myFormatCtx = theFormatCtx;
11
myStream = myFormatCtx->streams[theStreamId];
12
myStreamId = theStreamId;
13
- myCodecCtx = myStream->codec;
14
myPtsStartBase = detectPtsStartBase(theFormatCtx);
15
myPtsStartStream = unitsToSeconds(myStream->start_time);
16
+ myIsAttachedPic = stAV::isAttachedPicture(myStream);
17
+ if(stAV::getCodecType(myStream) != getCodecType()) {
18
+ signals.onError(stCString("Internal error: unsupported codec type"));
19
+ deinit();
20
+ return false;
21
+ }
22
+#ifdef ST_AV_NEWCODECPAR
23
+ myCodecAutoId = myStream->codecpar->codec_id;
24
+ myCodecCtx = avcodec_alloc_context3(NULL);
25
+ if(avcodec_parameters_to_context(myCodecCtx, myStream->codecpar) < 0) {
26
+ signals.onError(stCString("Internal error: unable to copy codec parameters"));
27
+ deinit();
28
+ return false;
29
+ }
30
+
31
+#else
32
+ myCodecCtx = stAV::getCodecCtx(myStream);
33
+ myCodecAutoId = myCodecCtx->codec_id;
34
+#endif
35
+
36
myGetFrmtInit = myCodecCtx->get_format;
37
#if(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(55, 0, 0))
38
myGetBuffInit = myCodecCtx->get_buffer2;
39
#endif
40
- myIsAttachedPic = stAV::isAttachedPicture(myStream);
41
+
42
+ if(myCodecAutoId == AV_CODEC_ID_TEXT) {
43
+ return true; // special case - decoder is not needed
44
+ }
45
+
46
+ myCodec = NULL;
47
+ myCodecAuto = avcodec_find_decoder(myCodecAutoId);
48
+ if(myCodecAuto == NULL) {
49
+ switch(getCodecType()) {
50
+ case AVMEDIA_TYPE_VIDEO:
51
+ signals.onError(stCString("FFmpeg: Video codec not found"));
52
+ break;
53
+ case AVMEDIA_TYPE_AUDIO:
54
+ signals.onError(stCString("FFmpeg: Audio codec not found"));
55
+ break;
56
+ case AVMEDIA_TYPE_SUBTITLE:
57
+ signals.onError(stCString("FFmpeg: Subtitle codec not found"));
58
+ break;
59
+ default:
60
+ signals.onError(stCString("FFmpeg: codec not found"));
61
+ break;
62
+ }
63
+ deinit();
64
+ return false;
65
+ }
66
+
67
return true;
68
}
69
70
71
myFileName.clear();
72
myFormatCtx = NULL;
73
myStream = NULL;
74
+ if(myCodec != NULL) {
75
+ fillCodecInfo(NULL);
76
+ }
77
+#ifdef ST_AV_NEWCODECPAR
78
+ if(myCodecCtx != NULL) {
79
+ avcodec_free_context(&myCodecCtx);
80
+ }
81
+#else
82
if(myCodec != NULL && myCodecCtx != NULL) {
83
avcodec_close(myCodecCtx);
84
myCodecCtx->get_format = myGetFrmtInit;
85
#if(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(55, 0, 0))
86
myCodecCtx->get_buffer2 = myGetBuffInit;
87
#endif
88
- fillCodecInfo(NULL);
89
}
90
+#endif
91
myCodec = NULL;
92
myCodecAuto = NULL;
93
+ myCodecAutoId = AV_CODEC_ID_NONE;
94
myCodecCtx = NULL;
95
myGetFrmtInit = NULL;
96
myGetBuffInit = NULL;
97
sview-17_04.tar.gz/StMoviePlayer/StVideo/StAVPacketQueue.h -> sview-20_08.tar.gz/StMoviePlayer/StVideo/StAVPacketQueue.h
Changed
43
1
2
ST_LOCAL void clear();
3
4
/**
5
+ * Return codec type.
6
+ */
7
+ ST_LOCAL virtual AVMediaType getCodecType() const = 0;
8
+
9
+ /**
10
* Close stream.
11
*/
12
ST_LOCAL virtual void deinit();
13
14
/**
15
* Open stream.
16
*/
17
- ST_LOCAL virtual bool init(AVFormatContext* theFormatCtx,
18
- const unsigned int theStreamId,
19
- const StString& theFileName);
20
+ ST_LOCAL bool init(AVFormatContext* theFormatCtx,
21
+ const unsigned int theStreamId,
22
+ const StString& theFileName);
23
24
protected: //! @name Fields should be full-controlled by heirs
25
26
27
AVCodecContext* myCodecCtx; //!< codec context
28
AVCodec* myCodec; //!< codec
29
AVCodec* myCodecAuto; //!< original codec (autodetected - before overriding)
30
+ AVCodecID myCodecAutoId; //!< original code id
31
typedef AVPixelFormat (*aGetFrmt_t)(AVCodecContext* , const AVPixelFormat* );
32
typedef int (*aGetBuf2_t)(AVCodecContext* , AVFrame* frame, int );
33
aGetFrmt_t myGetFrmtInit;
34
35
double mySizeSeconds; //!< cumulative packets length in seconds
36
mutable StMutex myMutex; //!< lock for thread-safety
37
38
+ protected:
39
+
40
StString myCodecName; //!< active codec name
41
StString myCodecDesc; //!< active codec description
42
StString myCodecStr; //!< active codec description
43
sview-17_04.tar.gz/StMoviePlayer/StVideo/StAudioQueue.cpp -> sview-20_08.tar.gz/StMoviePlayer/StVideo/StAudioQueue.cpp
Changed
102
1
2
return false;
3
}
4
5
- if(!StAVPacketQueue::init(theFormatCtx, theStreamId, theFileName)
6
- || myCodecCtx->codec_type != AVMEDIA_TYPE_AUDIO) {
7
+ if(!StAVPacketQueue::init(theFormatCtx, theStreamId, theFileName)) {
8
signals.onError(stCString("FFmpeg: invalid stream"));
9
deinit();
10
return false;
11
}
12
13
- // get AUDIO codec
14
- myCodec = avcodec_find_decoder(myCodecCtx->codec_id);
15
- if(myCodec == NULL) {
16
- signals.onError(stCString("FFmpeg: audio codec not found"));
17
- deinit();
18
- return false;
19
- }
20
#if(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(53, 8, 0))
21
- if(avcodec_open2(myCodecCtx, myCodec, NULL) < 0) {
22
+ if(avcodec_open2(myCodecCtx, myCodecAuto, NULL) < 0) {
23
#else
24
- if(avcodec_open(myCodecCtx, myCodec) < 0) {
25
+ if(avcodec_open(myCodecCtx, myCodecAuto) < 0) {
26
#endif
27
signals.onError(stCString("FFmpeg: could not open audio codec"));
28
deinit();
29
return false;
30
}
31
+ myCodec = myCodecAuto;
32
33
// setup buffers
34
if(!initBuffers()) {
35
36
);
37
}
38
myDbgPrevQueued = aQueued;
39
+#else
40
+ (void )myDbgPrevQueued;
41
#endif
42
43
if((aState == AL_PLAYING
44
45
int anAudioPktSize = thePacket->getSize();
46
bool checkMoreFrames = false;
47
int isGotFrame = 0;
48
+ bool toSendPacket = true;
49
// packet could store multiple frames
50
for(;;) {
51
while(anAudioPktSize > 0) {
52
int aDataSize = (int )myBufferSrc.getBufferSizeWhole();
53
54
- #if(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(52, 23, 0))
55
+ #if(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(57, 106, 102))
56
+ (void )aDataSize;
57
+ if(toSendPacket) {
58
+ const int aRes = avcodec_send_packet(myCodecCtx, thePacket->getType() == StAVPacket::DATA_PACKET ? thePacket->getAVpkt() : NULL);
59
+ if(aRes < 0 && aRes != AVERROR_EOF) {
60
+ anAudioPktSize = 0;
61
+ break;
62
+ }
63
+ toSendPacket = false;
64
+ }
65
+
66
+ myFrame.reset();
67
+ const int aRes2 = avcodec_receive_frame(myCodecCtx, myFrame.Frame);
68
+ if(aRes2 < 0) {
69
+ anAudioPktSize = 0;
70
+ break;
71
+ }
72
+ isGotFrame = 1;
73
+ int aLen1 = 0; // dummy for code compatible with old syntax
74
+ #elif(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(52, 23, 0))
75
StAVPacket anAvPkt;
76
anAvPkt.getAVpkt()->data = (uint8_t* )anAudioPktData;
77
anAvPkt.getAVpkt()->size = anAudioPktSize;
78
+ (void )toSendPacket;
79
80
#if(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(53, 40, 0))
81
- //av_frame_unref(myFrame.Frame);
82
(void )aDataSize;
83
myFrame.reset();
84
const int aLen1 = avcodec_decode_audio4(myCodecCtx, myFrame.Frame,
85
86
aPts = 0.0;
87
continue;
88
}
89
+ case StAVPacket::DATA_PACKET: {
90
+ break;
91
+ }
92
+ case StAVPacket::LAST_PACKET: {
93
+ #if(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(57, 106, 102))
94
+ break; // redirect NULL packet to avcodec_send_packet()
95
+ #else
96
+ continue;
97
+ #endif
98
+ }
99
case StAVPacket::END_PACKET: {
100
pushPlayEvent(ST_PLAYEVENT_NONE);
101
// TODO (Kirill Gavrilov#3#) improve file-by-file playback
102
sview-17_04.tar.gz/StMoviePlayer/StVideo/StAudioQueue.h -> sview-20_08.tar.gz/StMoviePlayer/StVideo/StAudioQueue.h
Changed
24
1
2
}
3
4
/**
5
+ * Return codec type.
6
+ */
7
+ ST_LOCAL virtual AVMediaType getCodecType() const ST_ATTR_OVERRIDE { return AVMEDIA_TYPE_AUDIO; }
8
+
9
+ /**
10
* Initialization function.
11
* @param theFormatCtx pointer to video format context
12
* @param theStreamId stream id in video format context
13
* @return true if no error
14
*/
15
- ST_LOCAL virtual bool init(AVFormatContext* theFormatCtx,
16
- const unsigned int theStreamId,
17
- const StString& theFileName) ST_ATTR_OVERRIDE;
18
+ ST_LOCAL bool init(AVFormatContext* theFormatCtx,
19
+ const unsigned int theStreamId,
20
+ const StString& theFileName);
21
22
/**
23
* Clean function.
24
sview-17_04.tar.gz/StMoviePlayer/StVideo/StSubtitleQueue.cpp -> sview-20_08.tar.gz/StMoviePlayer/StVideo/StSubtitleQueue.cpp
Changed
124
1
2
myOutQueue(theSubtitlesQueue),
3
myThread(NULL),
4
evDowntime(true),
5
+ myImageScale(1.0f),
6
toQuit(false) {
7
myThread = new StThread(threadFunction, (void* )this, "StSubtitleQueue");
8
}
9
10
bool StSubtitleQueue::init(AVFormatContext* theFormatCtx,
11
const unsigned int theStreamId,
12
const StString& theFileName) {
13
- if(!StAVPacketQueue::init(theFormatCtx, theStreamId, theFileName)
14
- || myCodecCtx->codec_type != AVMEDIA_TYPE_SUBTITLE) {
15
+ myImageScale = 1.0f;
16
+ if(!StAVPacketQueue::init(theFormatCtx, theStreamId, theFileName)) {
17
signals.onError(stCString("FFmpeg: invalid stream"));
18
deinit();
19
return false;
20
}
21
22
-#if(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(54, 51, 100))
23
- if(myCodecCtx->codec_id != AV_CODEC_ID_TEXT) {
24
-#else
25
- if(myCodecCtx->codec_id != CODEC_ID_TEXT) {
26
-#endif
27
- // find the decoder for the subtitles stream
28
- myCodec = avcodec_find_decoder(myCodecCtx->codec_id);
29
- if(myCodec == NULL) {
30
- signals.onError(stCString("FFmpeg: Subtitle decoder not found"));
31
- deinit();
32
- return false;
33
- }
34
-
35
+ if(myCodecAutoId != AV_CODEC_ID_TEXT) {
36
// open SUBTITLE codec
37
#if(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(53, 8, 0))
38
- if(avcodec_open2(myCodecCtx, myCodec, NULL) < 0) {
39
+ if(avcodec_open2(myCodecCtx, myCodecAuto, NULL) < 0) {
40
#else
41
- if(avcodec_open(myCodecCtx, myCodec) < 0) {
42
+ if(avcodec_open(myCodecCtx, myCodecAuto) < 0) {
43
#endif
44
signals.onError(stCString("FFmpeg: Could not open subtitle codec"));
45
deinit();
46
return false;
47
}
48
+ myCodec = myCodecAuto;
49
50
// initialize ASS parser
51
#if(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(52, 95, 0))
52
53
myCodecCtx->subtitle_header_size);
54
#endif
55
}
56
+ if(myCodecAuto != NULL && StString(myCodecAuto->name).isEquals(stCString("pgssub"))) {
57
+ myImageScale = 0.5f;
58
+ }
59
fillCodecInfo(myCodec);
60
return true;
61
}
62
63
myOutQueue->clear();
64
continue;
65
}
66
+ case StAVPacket::DATA_PACKET: {
67
+ break;
68
+ }
69
+ case StAVPacket::LAST_PACKET: {
70
+ continue; // ignore as avcodec_send_packet() is not used
71
+ }
72
case StAVPacket::END_PACKET: {
73
if(toQuit) {
74
return;
75
76
77
StHandle<StSubItem> aNewSubItem = new StSubItem(aPts, aPts + aDuration);
78
aNewSubItem->Image.initTrash(StImagePlane::ImgRGBA, aRect->w, aRect->h);
79
+ aNewSubItem->Scale = myImageScale;
80
+
81
+ #if(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(57, 9, 100))
82
+ uint8_t** anImgData = aRect->data;
83
+ int* anImgLineSizes = aRect->linesize;
84
+ #else
85
+ uint8_t** anImgData = aRect->pict.data;
86
+ int* anImgLineSizes = aRect->pict.linesize;
87
+ #endif
88
89
SwsContext* aCtxToRgb = sws_getContext(aRect->w, aRect->h, stAV::PIX_FMT::PAL8,
90
aRect->w, aRect->h, stAV::PIX_FMT::RGBA32,
91
92
}
93
94
uint8_t* aDstData[4] = {
95
- (uint8_t* )aNewSubItem->Image.getData(),
96
- NULL,
97
- NULL,
98
- NULL
99
+ (uint8_t* )aNewSubItem->Image.getData(), NULL, NULL, NULL
100
};
101
/*const*/ int aDstLinesize[4] = {
102
- (int )aNewSubItem->Image.getSizeRowBytes(),
103
- 0,
104
- 0,
105
- 0
106
+ (int )aNewSubItem->Image.getSizeRowBytes(), 0, 0, 0
107
};
108
109
sws_scale(aCtxToRgb,
110
- aRect->pict.data, aRect->pict.linesize,
111
+ anImgData, anImgLineSizes,
112
0, aRect->h,
113
aDstData, aDstLinesize);
114
sws_freeContext(aCtxToRgb);
115
116
}
117
case SUBTITLE_ASS: {
118
StString aTextData = aRect->ass;
119
- StHandle<StSubItem> aNewSubItem = myASS.parseEvent(aTextData, aPts);
120
+ StHandle<StSubItem> aNewSubItem = myASS.parseEvent(aTextData, aPts, aDuration);
121
if(!aNewSubItem.isNull()) {
122
myOutQueue->push(aNewSubItem);
123
}
124
sview-17_04.tar.gz/StMoviePlayer/StVideo/StSubtitleQueue.h -> sview-20_08.tar.gz/StMoviePlayer/StVideo/StSubtitleQueue.h
Changed
32
1
2
}
3
4
/**
5
+ * Return codec type.
6
+ */
7
+ ST_LOCAL virtual AVMediaType getCodecType() const ST_ATTR_OVERRIDE { return AVMEDIA_TYPE_SUBTITLE; }
8
+
9
+ /**
10
* Initialization function.
11
* @param theFormatCtx pointer to video format context
12
* @param streamId stream id in video format context
13
* @return true if no error
14
*/
15
- ST_LOCAL virtual bool init(AVFormatContext* theFormatCtx,
16
- const unsigned int theStreamId,
17
- const StString& theFileName) ST_ATTR_OVERRIDE;
18
+ ST_LOCAL bool init(AVFormatContext* theFormatCtx,
19
+ const unsigned int theStreamId,
20
+ const StString& theFileName);
21
22
/**
23
* Clean function.
24
25
StThread* myThread; //!< decoding loop thread
26
StSubtitlesASS myASS; //!< ASS subtitles parser
27
StCondition evDowntime;
28
+ float myImageScale;
29
volatile bool toQuit;
30
31
};
32
sview-17_04.tar.gz/StMoviePlayer/StVideo/StSubtitlesASS.cpp -> sview-20_08.tar.gz/StMoviePlayer/StVideo/StSubtitlesASS.cpp
Changed
83
1
2
/**
3
- * Copyright © 2011-2014 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2011-2020 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* StMoviePlayer program is free software: you can redistribute it and/or modify
7
* it under the terms of the GNU General Public License as published by
8
9
if(*anIter.getBufferHere() == stUtf8_t('i')) {
10
// italic
11
if( *anIter.getBufferNext() == stUtf8_t('1')) {
12
- ///aText += "<i>"; // on
13
+ aText += "<i>";
14
} else if(*anIter.getBufferNext() == stUtf8_t('0')) {
15
- ///aText += "</i>"; // off
16
+ aText += "</i>";
17
}
18
} else if(*anIter.getBufferHere() == stUtf8_t('b')) {
19
// bold
20
if( *anIter.getBufferNext() == stUtf8_t('1')) {
21
- ///aText += "<b>"; // on
22
+ aText += "<b>";
23
} else if(*anIter.getBufferNext() == stUtf8_t('0')) {
24
- ///aText += "</b>"; // off
25
+ aText += "</b>";
26
}
27
- }// else
28
+ } else if(*anIter.getBufferHere() == stUtf8_t('u')) {
29
+ // underline
30
+ if( *anIter.getBufferNext() == stUtf8_t('1')) {
31
+ //aText += "<u>";
32
+ } else if(*anIter.getBufferNext() == stUtf8_t('0')) {
33
+ //aText += "</u>";
34
+ }
35
+ } else if(*anIter.getBufferHere() == stUtf8_t('s')) {
36
+ // strikeout
37
+ if( *anIter.getBufferNext() == stUtf8_t('1')) {
38
+ //aText += "<s>";
39
+ } else if(*anIter.getBufferNext() == stUtf8_t('0')) {
40
+ //aText += "</s>";
41
+ }
42
+ } else if(*anIter.getBufferHere() == stUtf8_t('f')) {
43
+ if(*anIter.getBufferNext() == stUtf8_t('s')) {
44
+ // font size
45
+ } else if(*anIter.getBufferNext() == stUtf8_t('n')) {
46
+ // font name
47
+ }
48
+ }
49
+ // else
50
51
// search for trailing bracket
52
while(*anIter != stUtf32_t('}') && *anIter != 0) {
53
54
aStart = anIter.getIndex() + 1;
55
}
56
}
57
+ if(aStart != 0) {
58
+ aText += theText.subString(aStart, theText.Length);
59
+ }
60
if(!aText.isEmpty()) {
61
// replace only if text contains style codes
62
theText = aText;
63
64
}
65
66
StHandle<StSubItem> StSubtitlesASS::parseEvent(const StString& theString,
67
- const double thePts) {
68
+ double thePts,
69
+ double theDuration) {
70
if(!isValid() || !theString.isStartsWithIgnoreCase(HEADER_Dialog)) {
71
return StHandle<StSubItem>();
72
}
73
74
parseStyle(aText);
75
76
double aDuration = parseTime(aList->getValue(myIdPtsEnd)) - parseTime(aList->getValue(myIdPtsStart));
77
+ if(aDuration <= 0.0) {
78
+ aDuration = theDuration; // why ASS information is wrong here on current FFmpeg?
79
+ }
80
aText.replaceFast(ST_CRLF_REDUNDANT, ST_CRLF_REPLACEMENT);
81
aText.replaceFast(ST_ASS_NEWLINE, ST_NEWLINE_REPLACEMENT);
82
aText.replaceFast(ST_ASS_NEWLINE2, ST_NEWLINE_REPLACEMENT);
83
sview-17_04.tar.gz/StMoviePlayer/StVideo/StSubtitlesASS.h -> sview-20_08.tar.gz/StMoviePlayer/StVideo/StSubtitlesASS.h
Changed
18
1
2
/**
3
- * Copyright © 2011-2014 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2011-2020 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* StMoviePlayer program is free software: you can redistribute it and/or modify
7
* it under the terms of the GNU General Public License as published by
8
9
* Parse the dialog event and returns a subtitle item.
10
*/
11
ST_LOCAL StHandle<StSubItem> parseEvent(const StString& theString,
12
- const double thePts);
13
+ double thePts,
14
+ double theDuration);
15
16
private:
17
18
sview-17_04.tar.gz/StMoviePlayer/StVideo/StVideo.cpp -> sview-20_08.tar.gz/StMoviePlayer/StVideo/StVideo.cpp
Changed
563
1
2
#include "../StMoviePlayerInfo.h"
3
#include "../StMoviePlayerStrings.h"
4
5
+#include "../StImageViewer/StImagePluginInfo.h"
6
+
7
#include <StStrings/StFormatTime.h>
8
+#include <StAV/StAVIOJniHttpContext.h>
9
10
using namespace StMoviePlayerStrings;
11
12
13
aStVideo->mainLoop();
14
return SV_THREAD_RETURN 0;
15
}
16
+
17
+#ifdef ST_AV_NEWCODECPAR
18
+ /**
19
+ * Format framerate value.
20
+ */
21
+ static StString formatFps(double theVal) {
22
+ //const uint64_t aVal = lrintf(theVal * 100.0);
23
+ const uint64_t aVal = uint64_t(theVal * 100.0 + 0.5);
24
+ char aBuff[256];
25
+ if(aVal == 0) {
26
+ stsprintf(aBuff, sizeof(aBuff), "%1.4f", theVal);
27
+ } else if(aVal % 100) {
28
+ stsprintf(aBuff, sizeof(aBuff), "%3.2f", theVal);
29
+ } else if(aVal % (100 * 1000)) {
30
+ stsprintf(aBuff, sizeof(aBuff), "%1.0f", theVal);
31
+ } else {
32
+ stsprintf(aBuff, sizeof(aBuff), "%1.0fk", theVal / 1000);
33
+ }
34
+ return aBuff;
35
+ }
36
+#endif
37
+
38
+ /**
39
+ * Format stream info.
40
+ */
41
+ static StString formatStreamInfo(const AVStream* theStream) {
42
+ AVCodecContext* aCodecCtx = stAV::getCodecCtx(theStream);
43
+ char aFrmtBuff[4096] = {};
44
+ avcodec_string(aFrmtBuff, sizeof(aFrmtBuff), aCodecCtx, 0);
45
+ StString aStreamInfo(aFrmtBuff);
46
+
47
+ #ifdef ST_AV_NEWCODECPAR
48
+ //aStreamInfo = aStreamInfo + ", " + theStream->codec_info_nb_frames + ", " + theStream->time_base.num + "/" + theStream->time_base.den;
49
+ if(theStream->sample_aspect_ratio.num && av_cmp_q(theStream->sample_aspect_ratio, theStream->codecpar->sample_aspect_ratio)) {
50
+ AVRational aDispAspectRatio;
51
+ av_reduce(&aDispAspectRatio.num, &aDispAspectRatio.den,
52
+ theStream->codecpar->width * int64_t(theStream->sample_aspect_ratio.num),
53
+ theStream->codecpar->height * int64_t(theStream->sample_aspect_ratio.den),
54
+ 1024 * 1024);
55
+ aStreamInfo = aStreamInfo + ", SAR " + theStream->sample_aspect_ratio.num + ":" + theStream->sample_aspect_ratio.den
56
+ + " DAR " + aDispAspectRatio.num + ":" + aDispAspectRatio.den;
57
+ }
58
+
59
+ if(theStream->codecpar->codec_type == AVMEDIA_TYPE_VIDEO) {
60
+ if(theStream->avg_frame_rate.den != 0 && theStream->avg_frame_rate.num != 0) {
61
+ aStreamInfo += StString(", ") + formatFps(av_q2d(theStream->avg_frame_rate)) + " fps";
62
+ }
63
+ if(theStream->r_frame_rate.den != 0 && theStream->r_frame_rate.num != 0) {
64
+ aStreamInfo += StString(", ") + formatFps(av_q2d(theStream->r_frame_rate)) + " tbr";
65
+ }
66
+ if(theStream->time_base.den != 0 && theStream->time_base.num != 0) {
67
+ aStreamInfo += StString(", ") + formatFps(1 / av_q2d(theStream->time_base)) + " tbn";
68
+ }
69
+ if(aCodecCtx->time_base.den != 0 && aCodecCtx->time_base.num != 0) {
70
+ aStreamInfo += StString(", ") + formatFps(1 / av_q2d(aCodecCtx->time_base)) + " tbc";
71
+ }
72
+ }
73
+ #endif
74
+ return aStreamInfo;
75
+ }
76
}
77
78
+const char* StVideo::ST_IMAGES_MIME_STRING = ST_IMAGE_PLUGIN_MIME_CHAR;
79
const char* StVideo::ST_VIDEOS_MIME_STRING = ST_VIDEO_PLUGIN_MIME_CHAR;
80
81
StVideo::StVideo(const std::string& theALDeviceName,
82
83
: myMimesVideo(ST_VIDEOS_MIME_STRING),
84
myMimesAudio(ST_AUDIOS_MIME_STRING),
85
myMimesSubs(ST_SUBTIT_MIME_STRING),
86
+ myMimesImages(ST_IMAGES_MIME_STRING),
87
myResMgr(theResMgr),
88
myLangMap(theLangMap),
89
mySlaveCtx(NULL),
90
91
// open video file
92
StString aFileName, aDummy;
93
StFileNode::getFolderAndFile(theFileToLoad, aDummy, aFileName);
94
- AVFormatContext* aFormatCtx = NULL;
95
96
StHandle<StAVIOContext> anIOContext;
97
if(StFileNode::isContentProtocolPath(theFileToLoad)) {
98
99
if(aFileDescriptor != -1) {
100
StHandle<StAVIOFileContext> aFileCtx = new StAVIOFileContext();
101
if(aFileCtx->openFromDescriptor(aFileDescriptor, "rb")) {
102
- aFormatCtx = avformat_alloc_context();
103
- aFormatCtx->pb = aFileCtx->getAvioContext();
104
anIOContext = aFileCtx;
105
}
106
}
107
}
108
+#if defined(__ANDROID__)
109
+ else if(theFileToLoad.isStartsWith(stCString("https://"))) {
110
+ static const bool hasHttpsProtocol = stAV::isEnabledInputProtocol("https");
111
+ if(!hasHttpsProtocol) {
112
+ StHandle<StAVIOJniHttpContext> aHttpCtx = new StAVIOJniHttpContext();
113
+ if(aHttpCtx->open(theFileToLoad)) {
114
+ anIOContext = aHttpCtx;
115
+ }
116
+ }
117
+ }
118
+#endif
119
+ AVFormatContext* aFormatCtx = NULL;
120
+ if(!anIOContext.isNull()) {
121
+ aFormatCtx = avformat_alloc_context();
122
+ aFormatCtx->pb = anIOContext->getAvioContext();
123
+ }
124
125
#if(LIBAVFORMAT_VERSION_INT >= AV_VERSION_INT(53, 2, 0))
126
int avErrCode = avformat_open_input(&aFormatCtx, theFileToLoad.toCString(), NULL, NULL);
127
128
129
theInfo.Duration = stMax(theInfo.Duration, stAV::unitsToSeconds(aFormatCtx->duration));
130
for(unsigned int aStreamId = 0; aStreamId < aFormatCtx->nb_streams; ++aStreamId) {
131
- AVStream* aStream = aFormatCtx->streams[aStreamId];
132
+ AVStream* aStream = aFormatCtx->streams[aStreamId];
133
+ const AVMediaType aCodecType = stAV::getCodecType(aStream);
134
theInfo.Duration = stMax(theInfo.Duration, stAV::unitsToSeconds(aStream, aStream->duration));
135
136
- if(aStream->codec->codec_type == AVMEDIA_TYPE_VIDEO) {
137
+ StString aLang = stAV::meta::readLang(aStream);
138
+ if(aLang == "und") {
139
+ aLang.clear();
140
+ }
141
+
142
+ if(aCodecType == AVMEDIA_TYPE_VIDEO) {
143
// video track
144
if(!myVideoMaster->isInitialized()) {
145
myVideoMaster->init(aFormatCtx, aStreamId, aTitleString, theNewParams);
146
147
}
148
} else if(!myVideoSlave->isInitialized()
149
&& !stAV::isAttachedPicture(aStream)) {
150
- myVideoSlave->init(aFormatCtx, aStreamId, "", theNewParams);
151
+ myVideoSlave->init(aFormatCtx, aStreamId, aTitleString, theNewParams);
152
if(myVideoSlave->isInitialized()) {
153
mySlaveCtx = aFormatCtx;
154
mySlaveStream = aStreamId;
155
156
}
157
}
158
}
159
- } else if(aStream->codec->codec_type == AVMEDIA_TYPE_AUDIO) {
160
+ } else if(aCodecType == AVMEDIA_TYPE_AUDIO) {
161
// audio track
162
- AVCodecContext* aCodecCtx = aStream->codec;
163
StString aCodecName;
164
- AVCodec* aCodec = avcodec_find_decoder(aCodecCtx->codec_id);
165
+ AVCodec* aCodec = avcodec_find_decoder(stAV::getCodecId(aStream));
166
if(aCodec != NULL) {
167
aCodecName = aCodec->name;
168
}
169
170
+ AVCodecContext* aCodecCtx = stAV::getCodecCtx (aStream);
171
StString aSampleFormat = stAV::audio::getSampleFormatString (aCodecCtx);
172
StString aSampleRate = stAV::audio::getSampleRateString (aCodecCtx);
173
StString aChannelLayout = stAV::audio::getChannelLayoutString(aCodecCtx);
174
175
- StString aLang;
176
- #if(LIBAVUTIL_VERSION_INT >= AV_VERSION_INT(51, 5, 0))
177
- stAV::meta::readTag(aStream, stCString("language"), aLang);
178
- #else
179
- aLang = aStream->language;
180
- #endif
181
- if(aLang == "und") {
182
- aLang.clear();
183
- }
184
-
185
StString aStreamTitle = aCodecName;
186
if(!aSampleRate.isEmpty()) {
187
aStreamTitle += StString(", ") + aSampleRate;
188
189
190
if(!myAudio->isInitialized()
191
&& (aPrefLangAudio.isEmpty() || aLang == aPrefLangAudio)
192
- && myAudio->init(aFormatCtx, aStreamId, "")) {
193
+ && myAudio->init(aFormatCtx, aStreamId, aTitleString)) {
194
theInfo.LoadedAudio = (int32_t )(theInfo.AudioList->size() - 1);
195
}
196
- } else if(aStream->codec->codec_type == AVMEDIA_TYPE_SUBTITLE) {
197
+ } else if(aCodecType == AVMEDIA_TYPE_SUBTITLE) {
198
// subtitles track
199
- AVCodecContext* aCodecCtx = aStream->codec;
200
StString aCodecName("PLAIN");
201
- AVCodec* aCodec = avcodec_find_decoder(aCodecCtx->codec_id);
202
+ AVCodec* aCodec = avcodec_find_decoder(stAV::getCodecId(aStream));
203
if(aCodec != NULL) {
204
aCodecName = aCodec->name;
205
}
206
207
- StString aLang;
208
- #if(LIBAVUTIL_VERSION_INT >= AV_VERSION_INT(51, 5, 0))
209
- stAV::meta::readTag(aStream, stCString("language"), aLang);
210
- #else
211
- aLang = aStream->language;
212
- #endif
213
- if(aLang == "und") {
214
- aLang.clear();
215
- }
216
-
217
StString aStreamTitle = aCodecName;
218
if(!aLang.isEmpty()) {
219
aStreamTitle += StString(" (") + aLang + ")";
220
221
&& !theInfo.AudioList->isEmpty()) {
222
for(unsigned int aStreamId = 0; aStreamId < aFormatCtx->nb_streams; ++aStreamId) {
223
AVStream* aStream = aFormatCtx->streams[aStreamId];
224
- if(aStream->codec->codec_type != AVMEDIA_TYPE_AUDIO) {
225
+ if(stAV::getCodecType(aStream) != AVMEDIA_TYPE_AUDIO) {
226
continue;
227
}
228
229
230
aLanguage = aStream->language;
231
#endif
232
if(aLanguage != aPrefLangAudio
233
- && myAudio->init(aFormatCtx, aStreamId, "")) {
234
+ && myAudio->init(aFormatCtx, aStreamId, aTitleString)) {
235
theInfo.LoadedAudio = anAudioStreamId;
236
break;
237
}
238
239
}
240
}
241
242
+ // read general information about streams
243
+ for(size_t aCtxIter = 0; aCtxIter < myCtxList.size(); ++aCtxIter) {
244
+ AVFormatContext* aFormatCtx = myCtxList[aCtxIter];
245
+
246
+ StString aFrmtInfo;
247
+ if(aFormatCtx->bit_rate != 0) {
248
+ aFrmtInfo += StString("bitrate: ") + (int64_t(aFormatCtx->bit_rate) / 1000) + " kb/s";
249
+ }
250
+ if(!aFrmtInfo.isEmpty()) {
251
+ StString aStreamInfoKey = StString("input ") + aCtxIter;
252
+ myFileInfoTmp->Info.add(StArgument(aStreamInfoKey, aFrmtInfo));
253
+ }
254
+
255
+ for(unsigned int aStreamId = 0; aStreamId < aFormatCtx->nb_streams; ++aStreamId) {
256
+ AVStream* aStream = aFormatCtx->streams[aStreamId];
257
+ StString aLang = stAV::meta::readLang(aStream);
258
+ if(aLang.isEmpty()) {
259
+ aLang = "und";
260
+ }
261
+
262
+ StString aStreamInfoKey = StString("steam ")
263
+ + (myCtxList.size() > 1 ? (StString() + aCtxIter + ":" + aStreamId) : (StString() + aStreamId))
264
+ + " [" + aLang + "]";
265
+ myFileInfoTmp->Info.add(StArgument(aStreamInfoKey, formatStreamInfo(aStream)));
266
+ }
267
+ }
268
+
269
if(!myVideoMaster->isInitialized() && !myAudio->isInitialized()) {
270
signals.onError(stCString("FFmpeg: Didn't found any video or audio streams"));
271
return false;
272
273
isSeekDone = doSeekStream(theFormatCtx, myVideoMaster->getId(), theSeekPts, toSeekBack);
274
} else if(myVideoSlave->isInContext(theFormatCtx)) {
275
isSeekDone = doSeekStream(theFormatCtx, myVideoSlave->getId(), theSeekPts, toSeekBack);
276
+ } else if(myAudio->isInContext(theFormatCtx)) {
277
+ //
278
+ } else if(mySubtitles->isInContext(theFormatCtx)) {
279
+ if(mySubtitles->getFileName().isEndsWithIgnoreCase(stCString(".srt"))) {
280
+ // workaround SRT seeking issues - make a heavy seek (usual size of SRT file is not greater than 200 KiB)
281
+ isSeekDone = doSeekStream(theFormatCtx, mySubtitles->getId(), 0.0, true);
282
+ } else {
283
+ isSeekDone = doSeekStream(theFormatCtx, mySubtitles->getId(), theSeekPts, toSeekBack);
284
+ }
285
}
286
if(!isSeekDone && myAudio->isInContext(theFormatCtx)) {
287
// if no video stream or seeking was failed - try to seek Audio stream
288
289
isSeekDone = av_seek_frame(theFormatCtx, -1, aSeekTarget, aFlags) >= 0;
290
if(!isSeekDone) {
291
#ifdef ST_DEBUG
292
- ST_ERROR_LOG("Disaster! Seeking to " + theSeekPts + " [" + theFormatCtx->filename + "] has failed.");
293
+ #if(LIBAVFORMAT_VERSION_INT >= AV_VERSION_INT(58, 7, 100))
294
+ const char* aFileName = theFormatCtx->url;
295
+ #else
296
+ const char* aFileName = theFormatCtx->filename;
297
+ #endif
298
+ ST_ERROR_LOG("Disaster! Seeking to " + theSeekPts + " [" + aFileName + "] has failed.");
299
#endif
300
}
301
}
302
303
304
if(!isSeekDone) {
305
ST_DEBUG_LOG("Error while seeking"
306
- + (aStream->codec->codec_type == AVMEDIA_TYPE_VIDEO ? " Video"
307
- : (aStream->codec->codec_type == AVMEDIA_TYPE_AUDIO ? " Audio" : " "))
308
+ + (stAV::getCodecType(aStream) == AVMEDIA_TYPE_VIDEO ? " Video"
309
+ : (stAV::getCodecType(aStream) == AVMEDIA_TYPE_AUDIO ? " Audio" : " "))
310
+ "stream to " + theSeekPts + "sec(" + (theSeekPts + stAV::unitsToSeconds(aStream, aStream->start_time)) + "sec)");
311
}
312
return isSeekDone;
313
314
doFlush();
315
if(myVideoMaster->isInitialized()) {
316
const StString aFileNameMaster = myVideoMaster->getFileName();
317
+ const StString aFileNameSlave = myVideoSlave ->getFileName();
318
AVFormatContext* aCtxMaster = myVideoMaster->getContext();
319
const signed int aStreamIdMaster = myVideoMaster->getId();
320
myVideoMaster->pushEnd();
321
322
myVideoMaster->init(aCtxMaster, aStreamIdMaster, aFileNameMaster, myCurrParams);
323
myVideoMaster->setSlave(NULL);
324
if(toDecodeSlave) {
325
- myVideoSlave->init(mySlaveCtx, mySlaveStream, "", myCurrParams);
326
+ myVideoSlave->init(mySlaveCtx, mySlaveStream, aFileNameSlave, myCurrParams);
327
myVideoMaster->setSlave(myVideoSlave);
328
}
329
myVideoMaster->pushStart();
330
331
332
StArrayList<StAVPacket> anAVPackets(myCtxList.size());
333
StArrayList<bool> aQueueIsFull(myCtxList.size());
334
+ StArrayList<bool> aQueueIsEmpty(myCtxList.size());
335
myPlayCtxList.clear();
336
size_t anEmptyQueues = 0;
337
size_t aCtxId = 0;
338
339
myPlayCtxList.add(aFormatCtx);
340
anAVPackets.add(StAVPacket(myCurrParams));
341
aQueueIsFull.add(false);
342
+ aQueueIsEmpty.add(false);
343
}
344
345
// reset target FPS
346
347
// read next packet
348
if(av_read_frame(aFormatCtx, aPacket.getAVpkt()) < 0) {
349
++anEmptyQueues;
350
+ if(!aQueueIsEmpty[aCtxId]) {
351
+ aQueueIsEmpty[aCtxId] = true;
352
+ // force decoding of last frame
353
+ const StAVPacket aDummyLastPacket(myCurrParams, StAVPacket::LAST_PACKET);
354
+ if(myVideoMaster->isInContext(aFormatCtx)) {
355
+ myVideoMaster->push(aDummyLastPacket);
356
+ }
357
+ if(myVideoSlave->isInContext(aFormatCtx)) {
358
+ myVideoSlave->push(aDummyLastPacket);
359
+ }
360
+ if(myAudio->isInContext(aFormatCtx)) {
361
+ myAudio->push(aDummyLastPacket);
362
+ }
363
+ if(mySubtitles->isInContext(aFormatCtx)) {
364
+ mySubtitles->push(aDummyLastPacket);
365
+ }
366
+ }
367
continue;
368
}
369
}
370
371
for(aCtxId = 0; aCtxId < myCtxList.size() && !myAudio->isInitialized(); ++aCtxId) {
372
aFormatCtx = myCtxList[aCtxId];
373
for(unsigned int aStreamId = 0; aStreamId < aFormatCtx->nb_streams; ++aStreamId) {
374
- if(aFormatCtx->streams[aStreamId]->codec->codec_type == AVMEDIA_TYPE_AUDIO) {
375
+ if(stAV::getCodecType(aFormatCtx->streams[aStreamId]) == AVMEDIA_TYPE_AUDIO) {
376
if(aCounter == anActiveStreamId) {
377
- myAudio->init(aFormatCtx, aStreamId, "");
378
+ myAudio->init(aFormatCtx, aStreamId, myFileList[aCtxId]);
379
myAudio->pushStart();
380
break;
381
}
382
383
for(aCtxId = 0; aCtxId < myCtxList.size() && !mySubtitles->isInitialized(); ++aCtxId) {
384
aFormatCtx = myCtxList[aCtxId];
385
for(unsigned int aStreamId = 0; aStreamId < aFormatCtx->nb_streams; ++aStreamId) {
386
- if(aFormatCtx->streams[aStreamId]->codec->codec_type == AVMEDIA_TYPE_SUBTITLE) {
387
+ if(stAV::getCodecType(aFormatCtx->streams[aStreamId]) == AVMEDIA_TYPE_SUBTITLE) {
388
if(aCounter == anActiveStreamId) {
389
- mySubtitles->init(aFormatCtx, aStreamId, "");
390
+ mySubtitles->init(aFormatCtx, aStreamId, myFileList[aCtxId]);
391
mySubtitles->pushStart();
392
break;
393
}
394
395
#endif
396
397
// All packets sent
398
+ bool isPendingPlayNext = false;
399
if(anEmptyQueues == myPlayCtxList.size()) {
400
bool areFlushed = false;
401
// It seems FFmpeg fail to seek the stream after all packets were read...
402
403
|| !mySubtitles->isEmpty() || !mySubtitles->isInDowntime()) {
404
StThread::sleep(10);
405
if(!areFlushed && (popPlayEvent(aSeekPts, toSeekBack) == ST_PLAYEVENT_NEXT)) {
406
+ isPendingPlayNext = true;
407
doFlush();
408
if(myAudio->isInitialized()) {
409
myAudio->pushPlayEvent(ST_PLAYEVENT_SEEK, 0.0);
410
}
411
areFlushed = true;
412
+ isPendingPlayNext = true;
413
}
414
}
415
// If video is played - always wait until audio played
416
- if(myVideoMaster->isInitialized() && myAudio->isInitialized()) {
417
- while(myAudio->stalIsAudioPlaying()) {
418
- StThread::sleep(10);
419
- if(!areFlushed && (popPlayEvent(aSeekPts, toSeekBack) == ST_PLAYEVENT_NEXT)) {
420
- doFlush();
421
- if(myAudio->isInitialized()) {
422
- myAudio->pushPlayEvent(ST_PLAYEVENT_SEEK, 0.0);
423
+ if(myVideoMaster->isInitialized()) {
424
+ if(myAudio->isInitialized()) {
425
+ while(myAudio->stalIsAudioPlaying()) {
426
+ StThread::sleep(10);
427
+ if(!areFlushed && (popPlayEvent(aSeekPts, toSeekBack) == ST_PLAYEVENT_NEXT)) {
428
+ isPendingPlayNext = true;
429
+ doFlush();
430
+ if(myAudio->isInitialized()) {
431
+ myAudio->pushPlayEvent(ST_PLAYEVENT_SEEK, 0.0);
432
+ }
433
+ areFlushed = true;
434
+ isPendingPlayNext = true;
435
+ break;
436
+ }
437
+ }
438
+ } else if(myDuration < (double )params.SlideShowDelay->getValue()) {
439
+ StTimer aDelayTimer;
440
+ aDelayTimer.restart(myDuration * 1000.0);
441
+ while(aDelayTimer.getElapsedTimeInSec() < (double )params.SlideShowDelay->getValue()) {
442
+ StThread::sleep(10);
443
+ if((popPlayEvent(aSeekPts, toSeekBack) == ST_PLAYEVENT_NEXT)) {
444
+ isPendingPlayNext = true;
445
+ break;
446
+ }
447
+ const bool isPaused = !isPlaying();
448
+ if(isPaused) {
449
+ aDelayTimer.pause();
450
+ } else {
451
+ aDelayTimer.resume();
452
}
453
- areFlushed = true;
454
}
455
}
456
}
457
+ if(isPendingPlayNext) {
458
+ // resend event after it was pop out
459
+ pushPlayEvent(ST_PLAYEVENT_NEXT);
460
+ break;
461
+ }
462
+
463
// end when any one in format context finished
464
myCurrParams->Timestamp = 0.0f;
465
break;
466
467
if(myAudio->isInitialized()) myAudio->pushEnd();
468
if(mySubtitles->isInitialized()) mySubtitles->pushEnd();
469
470
- // what for queues receive 'end-packet'
471
+ // wait for queues receive 'end-packet'
472
while(!myVideoMaster->isEmpty() || !myVideoMaster->isInDowntime()
473
|| !myAudio->isEmpty() || !myAudio->isInDowntime()
474
|| !myVideoSlave->isEmpty() || !myVideoSlave->isInDowntime()
475
476
dataResult->initWrapper(dataLeft);
477
}
478
479
- StString title = myLangMap->getValue(StMoviePlayerStrings::DIALOG_SAVE_SNAPSHOT);
480
- StMIMEList filter;
481
+ StOpenFileName anOpenInfo;
482
+ anOpenInfo.Title = myLangMap->getValue(StMoviePlayerStrings::DIALOG_SAVE_SNAPSHOT);
483
StString saveExt;
484
if(toSaveStereo) {
485
switch(theImgType) {
486
case StImageFile::ST_TYPE_PNG:
487
saveExt = "pns";
488
- filter.add(StMIME("image/pns", saveExt,
489
- "PNS - png stereo image, lossless"));
490
+ anOpenInfo.Filter.add(StMIME("image/pns", saveExt,
491
+ "PNS - png stereo image, lossless"));
492
break;
493
case StImageFile::ST_TYPE_JPEG:
494
saveExt = "jps";
495
- filter.add(StMIME("image/jps", saveExt,
496
- "JPS - jpeg stereo image, lossy"));
497
+ anOpenInfo.Filter.add(StMIME("image/jps", saveExt,
498
+ "JPS - jpeg stereo image, lossy"));
499
break;
500
default:
501
return false;
502
503
switch(theImgType) {
504
case StImageFile::ST_TYPE_PNG:
505
saveExt = "png";
506
- filter.add(StMIME("image/png", saveExt,
507
- "PNG image, lossless"));
508
+ anOpenInfo.Filter.add(StMIME("image/png", saveExt,
509
+ "PNG image, lossless"));
510
break;
511
case StImageFile::ST_TYPE_JPEG:
512
saveExt = "jpg";
513
- filter.add(StMIME("image/jpg", saveExt,
514
- "JPEG image, lossy"));
515
+ anOpenInfo.Filter.add(StMIME("image/jpg", saveExt,
516
+ "JPEG image, lossy"));
517
break;
518
default:
519
return false;
520
521
}
522
523
StString fileToSave;
524
- if(StFileNode::openFileDialog(myCurrNode->getFolderPath(), title, filter, fileToSave, true)) {
525
+ anOpenInfo.Folder = myCurrNode->getFolderPath();
526
+ if(StFileNode::openFileDialog(fileToSave, anOpenInfo, true)) {
527
if(StFileNode::getExtension(fileToSave) != saveExt) {
528
fileToSave += StString('.') + saveExt;
529
}
530
531
// wait for initial message
532
waitEvent();
533
if(toQuit) {
534
+ close();
535
myQuitEvent.set();
536
return;
537
}
538
539
540
if(myVideoMaster->isInContext(myCtxList[0])) {
541
myVideoTimer = new StVideoTimer(myVideoMaster, myAudio,
542
- 1000.0 * av_q2d(myCtxList[0]->streams[myVideoMaster->getId()]->codec->time_base));
543
+ 1000.0 * av_q2d(stAV::getCodecCtx(myCtxList[0]->streams[myVideoMaster->getId()])->time_base));
544
myVideoTimer->setAudioDelay(myAudioDelayMSec);
545
myVideoTimer->setBenchmark(myIsBenchmark);
546
} else if(myCtxList.size() > 1 && myVideoMaster->isInContext(myCtxList[1])) {
547
myVideoTimer = new StVideoTimer(myVideoMaster, myAudio,
548
- 1000.0 * av_q2d(myCtxList[1]->streams[myVideoMaster->getId()]->codec->time_base));
549
+ 1000.0 * av_q2d(stAV::getCodecCtx(myCtxList[1]->streams[myVideoMaster->getId()])->time_base));
550
myVideoTimer->setAudioDelay(myAudioDelayMSec);
551
myVideoTimer->setBenchmark(myIsBenchmark);
552
} else {
553
554
myPlayList->walkToNext(false);
555
}
556
if(toQuit) {
557
+ // make sure to close AVIO contexts from the same working thread,
558
+ // because some of them can be attached to specific thread (like StAVIOJniHttpContext to JavaVM)
559
+ close();
560
myQuitEvent.set();
561
return;
562
}
563
sview-17_04.tar.gz/StMoviePlayer/StVideo/StVideo.h -> sview-20_08.tar.gz/StMoviePlayer/StVideo/StVideo.h
Changed
78
1
2
public: //! @name public methods
3
4
static const char* ST_VIDEOS_MIME_STRING;
5
+ static const char* ST_IMAGES_MIME_STRING;
6
7
- ST_LOCAL const StMIMEList& getMimeListVideo() const {
8
- return myMimesVideo;
9
- }
10
+ ST_LOCAL const StMIMEList& getMimeListVideo() const { return myMimesVideo; }
11
12
- ST_LOCAL const StMIMEList& getMimeListAudio() const {
13
- return myMimesAudio;
14
- }
15
+ ST_LOCAL const StMIMEList& getMimeListAudio() const { return myMimesAudio; }
16
17
- ST_LOCAL const StMIMEList& getMimeListSubtitles() const {
18
- return myMimesSubs;
19
- }
20
+ ST_LOCAL const StMIMEList& getMimeListSubtitles() const { return myMimesSubs; }
21
+
22
+ ST_LOCAL const StMIMEList& getMimeListImages() const { return myMimesImages; }
23
24
/**
25
* Main constructor.
26
27
}
28
29
/**
30
+ * Set theater mode.
31
+ */
32
+ ST_LOCAL void setTheaterMode(bool theIsTheater) {
33
+ myVideoMaster->setTheaterMode(theIsTheater);
34
+ }
35
+
36
+ /**
37
* Stick to panorama 360 mode.
38
*/
39
ST_LOCAL void setStickPano360(bool theToStick) {
40
41
}
42
43
/**
44
+ * Set if JPS file should be read as Left/Right (TRUE) of as Right/Left (FALSE).
45
+ */
46
+ ST_LOCAL void setSwapJPS(bool theToSwap) { myVideoMaster->setSwapJPS(theToSwap); }
47
+
48
+ /**
49
* Retrieve information about currently played file.
50
*/
51
ST_LOCAL StHandle<StMovieInfo> getFileInfo(const StHandle<StStereoParams>& theParams) const;
52
53
StHandle<StBoolParam> UseOpenJpeg; //!< use OpenJPEG (libopenjpeg) instead of built-in jpeg2000 decoder
54
StHandle<StBoolParam> ToSearchSubs; //!< automatically search for additional subtitles/audio track files nearby video file
55
StHandle<StBoolParamNamed> ToTrackHeadAudio;//!< enable/disable head-tracking for audio listener
56
+ StHandle<StFloat32Param> SlideShowDelay; //!< slideshow delay
57
StHandle<StParamActiveStream> activeAudio; //!< active Audio stream
58
StHandle<StParamActiveStream> activeSubtitles; //!< active Subtitles stream
59
60
61
*/
62
ST_LOCAL void close();
63
64
+ /**
65
+ * Dispatch packets from format contexts to decoding queues.
66
+ */
67
ST_LOCAL void packetsLoop();
68
69
/**
70
71
StMIMEList myMimesVideo;
72
StMIMEList myMimesAudio;
73
StMIMEList myMimesSubs;
74
+ StMIMEList myMimesImages;
75
StHandle<StThread> myThread; //!< main loop thread
76
StHandle<StResourceManager> myResMgr; //!< resource manager
77
StHandle<StTranslations> myLangMap; //!< translations dictionary
78
sview-17_04.tar.gz/StMoviePlayer/StVideo/StVideoDxva2.cpp -> sview-20_08.tar.gz/StMoviePlayer/StVideo/StVideoDxva2.cpp
Changed
90
1
2
/**
3
* Destroy decoder.
4
*/
5
- virtual void decoderDestroy() ST_ATTR_OVERRIDE {
6
+ virtual void decoderDestroy(AVCodecContext* ) ST_ATTR_OVERRIDE {
7
myPoolsTmp[0].release();
8
myPoolsTmp[1].release();
9
myPoolsTmp[2].release();
10
11
};
12
13
void StDxva2Context::release() {
14
- decoderDestroy();
15
+ decoderDestroy(NULL);
16
if(myDecoderService != NULL) {
17
myDecoderService->Release();
18
myDecoderService = NULL;
19
20
bool StDxva2Context::decoderCreate(StVideoQueue& theVideo,
21
AVCodecContext* theCodecCtx) {
22
const StSignal<void (const StCString& )>& onError = theVideo.signals.onError;
23
- decoderDestroy();
24
+ decoderDestroy(theCodecCtx);
25
theCodecCtx->hwaccel_context = NULL;
26
27
uint32_t aNbGuids = 0;
28
GUID* aGuidList = NULL;
29
if(myDecoderService->GetDecoderDeviceGuids(&aNbGuids, &aGuidList) != S_OK) {
30
onError(stCString("StVideoQueue: Failed to retrieve decoder DXVA2 device GUIDs"));
31
- decoderDestroy();
32
+ decoderDestroy(theCodecCtx);
33
return false;
34
}
35
36
37
38
if(::IsEqualGUID(aDeviceGuid, GUID_NULL)) {
39
onError(stCString("StVideoQueue: No DXVA2 decoder device for codec found"));
40
- decoderDestroy();
41
+ decoderDestroy(theCodecCtx);
42
return false;
43
}
44
45
46
DXVA2_ConfigPictureDecode aBestCfg = {{0}};
47
if(myDecoderService->GetDecoderConfigurations(aDeviceGuid, &aDesc, NULL, &aNbConfigs, &aCfgList) != S_OK) {
48
onError(stCString("StVideoQueue: Unable to retrieve DXVA2 decoder configurations"));
49
- decoderDestroy();
50
+ decoderDestroy(theCodecCtx);
51
return false;
52
}
53
54
55
::CoTaskMemFree(aCfgList);
56
if(aBestScore == 0) {
57
onError(stCString("StVideoQueue: No valid DXVA2 decoder configuration available"));
58
- decoderDestroy();
59
+ decoderDestroy(theCodecCtx);
60
return false;
61
}
62
63
64
if(myD3dSurfaces == NULL
65
|| mySurfInfos == NULL) {
66
ST_ERROR_LOG(stCString("StVideoQueue: Unable to allocate surface arrays"));
67
- decoderDestroy();
68
+ decoderDestroy(theCodecCtx);
69
return false;
70
}
71
72
73
myD3dSurfaces, NULL);
74
if(anHRes != S_OK) {
75
onError(StString("StVideoQueue: Failed to create ") + myNbSurfaces + " video surfaces");
76
- decoderDestroy();
77
+ decoderDestroy(theCodecCtx);
78
return false;
79
}
80
81
82
myNbSurfaces, &myDxvaDecoder);
83
if(anHRes != S_OK) {
84
onError(stCString("StVideoQueue: Failed to create DXVA2 video decoder"));
85
- decoderDestroy();
86
+ decoderDestroy(theCodecCtx);
87
return false;
88
}
89
90
sview-17_04.tar.gz/StMoviePlayer/StVideo/StVideoQueue.cpp -> sview-20_08.tar.gz/StMoviePlayer/StVideo/StVideoQueue.cpp
Changed
970
1
2
/**
3
- * Copyright © 2009-2017 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2009-2019 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* StMoviePlayer program is free software: you can redistribute it and/or modify
7
* it under the terms of the GNU General Public License as published by
8
9
10
namespace {
11
12
-#if defined(__APPLE__) || defined(__ANDROID__)
13
- /**
14
- * Override pixel format.
15
- */
16
- AVPixelFormat stGetFormatYUV420P(AVCodecContext* /*theCtx*/,
17
- const AVPixelFormat* /*theFmt*/) {
18
- return stAV::PIX_FMT::YUV420P;
19
- }
20
-#endif
21
-
22
#if(LIBAVCODEC_VERSION_INT < AV_VERSION_INT(55, 0, 0))
23
/**
24
* Release the frame buffer (old API).
25
26
return avcodec_default_get_format(myCodecCtx, theFormats);
27
}
28
29
- for(const AVPixelFormat* aFormatIter = theFormats; *aFormatIter != -1; ++aFormatIter) {
30
+ for(const AVPixelFormat* aFormatIter = theFormats; *aFormatIter != stAV::PIX_FMT::NONE; ++aFormatIter) {
31
/*const AVPixFmtDescriptor* aDesc = av_pix_fmt_desc_get(*aFormatIter);
32
if(!(aDesc->flags & AV_PIX_FMT_FLAG_HWACCEL)) {
33
return *aFormatIter;
34
35
}
36
return *aFormatIter;
37
}
38
+ #elif defined(__APPLE__)
39
+ if(*aFormatIter == stAV::PIX_FMT::VIDEOTOOLBOX_VLD) {
40
+ if(!hwaccelInit()) {
41
+ myIsGpuFailed = true;
42
+ return avcodec_default_get_format(myCodecCtx, theFormats);
43
+ }
44
+ return *aFormatIter;
45
+ }
46
+ #elif defined(__ANDROID__)
47
+ if(*aFormatIter == AV_PIX_FMT_MEDIACODEC) {
48
+ // decoding into surface (like android.graphics.SurfaceTexture) is not yet support
49
+ return *aFormatIter;
50
+ }
51
#endif
52
}
53
54
55
}
56
isDone = true;
57
}
58
+ /*#elif defined(__APPLE__) // standard FFmpeg VideoToolbox wrapper is used - action is not needed
59
+ if(theFrame->format == stAV::PIX_FMT::VIDEOTOOLBOX_VLD) {
60
+ if(!myHWAccelCtx.isNull()) {
61
+ aResult = myHWAccelCtx->getFrameBuffer(*this, theFrame);
62
+ } else {
63
+ aResult = -1;
64
+ }
65
+ isDone = true;
66
+ }*/
67
#endif
68
if(!isDone) {
69
aResult = avcodec_default_get_buffer2(myCodecCtx, theFrame, theFlags);
70
71
return aResult;
72
}
73
74
-#if !defined(_WIN32)
75
+#if !defined(_WIN32) && !defined(__APPLE__)
76
bool StVideoQueue::hwaccelInit() { return false; }
77
#endif
78
79
80
myTextureQueue(theTextureQueue),
81
myHasDataState(false),
82
myMaster(theMaster),
83
-#if defined(__APPLE__)
84
- myCodecH264HW(avcodec_find_decoder_by_name("h264_vda")),
85
-#elif defined(__ANDROID__)
86
+#if defined(__ANDROID__)
87
myCodecH264HW(avcodec_find_decoder_by_name("h264_mediacodec")),
88
+ myCodecHevcHW(avcodec_find_decoder_by_name("hevc_mediacodec")),
89
+ myCodecVp9HW (avcodec_find_decoder_by_name("vp9_mediacodec")),
90
#endif
91
myCodecOpenJpeg(avcodec_find_decoder_by_name("libopenjpeg")),
92
myUseGpu(false),
93
94
myStFormatByUser(StFormat_AUTO),
95
myStFormatByName(StFormat_AUTO),
96
myStFormatInStream(StFormat_AUTO),
97
- myToStickPano360(false) {
98
+ myIsTheaterMode(false),
99
+ myToStickPano360(false),
100
+ myToSwapJps(false) {
101
#ifdef ST_USE64PTR
102
myFrame.Frame->opaque = (void* )stAV::NOPTS_VALUE;
103
#else
104
105
const bool theToUseGpu) {
106
// close previous codec
107
if(myCodec != NULL) {
108
- avcodec_close(myCodecCtx);
109
+ myCodec = NULL;
110
fillCodecInfo(NULL);
111
+ #ifdef ST_AV_NEWCODECPAR
112
+ avcodec_free_context(&myCodecCtx);
113
+ myCodecCtx = avcodec_alloc_context3(NULL);
114
+ if(avcodec_parameters_to_context(myCodecCtx, myStream->codecpar) < 0) {
115
+ signals.onError(stCString("Internal error: unable to copy codec parameters"));
116
+ return false;
117
+ }
118
+ #else
119
+ avcodec_close(myCodecCtx);
120
+ #endif
121
}
122
- myCodec = NULL;
123
+
124
+ myCodecCtx->opaque = this;
125
+ myCodecCtx->get_format = stGetFrameFormat;
126
+#if(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(55, 0, 0))
127
+ if(check720in1080()) {
128
+ myCodecCtx->flags2 |= AV_CODEC_FLAG2_IGNORE_CROP;
129
+ }
130
+ myCodecCtx->get_buffer2 = stGetFrameBuffer2;
131
+#else
132
+ myCodecCtx->get_buffer = stGetFrameBuffer1;
133
+ myCodecCtx->release_buffer = stReleaseFrameBuffer;
134
+#endif
135
136
// configure the codec
137
myCodecCtx->codec_id = theCodec->id;
138
139
av_dict_set(&anOpts, "refcounted_frames", "1", 0);
140
#endif
141
142
- int aNbThreads = theToUseGpu ? 1 : StThread::countLogicalProcessors();
143
+ // attached pics are sparse, therefore we would not want to delay their decoding till EOF
144
+ int aNbThreads = theToUseGpu || isAttachedPicture()
145
+ ? 1
146
+ : StThread::countLogicalProcessors();
147
myCodecCtx->thread_count = aNbThreads;
148
#if(LIBAVCODEC_VERSION_INT < AV_VERSION_INT(52, 112, 0))
149
avcodec_thread_init(myCodecCtx, aNbThreads);
150
151
const unsigned int theStreamId,
152
const StString& theFileName,
153
const StHandle<StStereoParams>& theNewParams) {
154
- if(!StAVPacketQueue::init(theFormatCtx, theStreamId, theFileName)
155
- || myCodecCtx->codec_type != AVMEDIA_TYPE_VIDEO) {
156
+ if(!StAVPacketQueue::init(theFormatCtx, theStreamId, theFileName)) {
157
signals.onError(stCString("FFmpeg: invalid stream"));
158
deinit();
159
return false;
160
}
161
162
- // detect 720in1080 streams with cropping information
163
- const bool is720in1080 = (sizeX() == 1280) && (sizeY() == 720)
164
- && (getCodedSizeX() == 1920)
165
- && (getCodedSizeY() == 1080 || getCodedSizeY() == 1088);
166
-#if(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(55, 0, 0))
167
- if(is720in1080) {
168
- myCodecCtx->flags2 |= CODEC_FLAG2_IGNORE_CROP;
169
- }
170
-#endif
171
-
172
- // find the decoder for the video stream
173
- myCodecCtx->opaque = this;
174
- myCodecCtx->get_format = stGetFrameFormat;
175
-#if(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(55, 0, 0))
176
- myCodecCtx->get_buffer2 = stGetFrameBuffer2;
177
-#else
178
- myCodecCtx->get_buffer = stGetFrameBuffer1;
179
- myCodecCtx->release_buffer = stReleaseFrameBuffer;
180
-#endif
181
-
182
- myCodecAuto = avcodec_find_decoder(myCodecCtx->codec_id);
183
- if(myCodecAuto == NULL) {
184
- signals.onError(stCString("FFmpeg: Video codec not found"));
185
- deinit();
186
- return false;
187
- }
188
-
189
#if defined(_WIN32)
190
- myIsGpuFailed = myCodecCtx->codec_id != CodecIdMPEG2
191
- && myCodecCtx->codec_id != CodecIdH264
192
- && myCodecCtx->codec_id != CodecIdVC1
193
- && myCodecCtx->codec_id != CodecIdWMV3
194
- && myCodecCtx->codec_id != CodecIdVC1
195
- && myCodecCtx->codec_id != CodecIdHEVC;
196
+ myIsGpuFailed = myCodecAutoId != CodecIdMPEG2
197
+ && myCodecAutoId != CodecIdH264
198
+ && myCodecAutoId != CodecIdVC1
199
+ && myCodecAutoId != CodecIdWMV3
200
+ && myCodecAutoId != CodecIdHEVC;
201
+#elif defined(__APPLE__)
202
+ myIsGpuFailed = myCodecAutoId != CodecIdMPEG2
203
+ && myCodecAutoId != CodecIdH264
204
+ && myCodecAutoId != CodecIdHEVC;
205
#endif
206
207
bool isCodecOverridden = false;
208
if(myUseOpenJpeg
209
- && myCodecCtx->codec_id == CodecIdJpeg2K
210
+ && myCodecAutoId == CodecIdJpeg2K
211
&& myCodecOpenJpeg != NULL) {
212
isCodecOverridden = initCodec(myCodecOpenJpeg, false);
213
}
214
215
// open VIDEO codec
216
-#if defined(__APPLE__) || defined(__ANDROID__)
217
+#if defined(__ANDROID__)
218
AVCodec* aCodecGpu = NULL;
219
if(myUseGpu
220
- && StString(myCodecAuto->name).isEquals(stCString("h264"))
221
&& myCodecCtx->pix_fmt == stAV::PIX_FMT::YUV420P) {
222
- aCodecGpu = myCodecH264HW;
223
+ const StString anAutoCodecName(myCodecAuto->name);
224
+ if(anAutoCodecName.isEquals(stCString("h264"))) {
225
+ aCodecGpu = myCodecH264HW;
226
+ } else if(anAutoCodecName.isEquals(stCString("hevc"))) {
227
+ aCodecGpu = myCodecHevcHW;
228
+ } else if(anAutoCodecName.isEquals(stCString("vp9"))) {
229
+ aCodecGpu = myCodecVp9HW;
230
+ }
231
}
232
233
if(aCodecGpu != NULL) {
234
- myCodecCtx->get_format = stGetFormatYUV420P;
235
isCodecOverridden = initCodec(aCodecGpu, true);
236
- if(!isCodecOverridden) {
237
- myCodecCtx->get_format = myGetFrmtInit;
238
- }
239
}
240
if(!isCodecOverridden && !initCodec(myCodecAuto, false)) {
241
signals.onError(stCString("FFmpeg: Could not open video codec"));
242
243
myFrame.reset();
244
245
// compute PAR
246
- if(myStream->sample_aspect_ratio.num && av_cmp_q(myStream->sample_aspect_ratio, myStream->codec->sample_aspect_ratio)) {
247
+ if(myStream->sample_aspect_ratio.num && av_cmp_q(myStream->sample_aspect_ratio, myCodecCtx->sample_aspect_ratio)) {
248
myPixelRatio = GLfloat(myStream->sample_aspect_ratio.num) / GLfloat(myStream->sample_aspect_ratio.den);
249
} else {
250
if(myCodecCtx->sample_aspect_ratio.num == 0 ||
251
252
switch(aSpherical->projection) {
253
case AV_SPHERICAL_EQUIRECTANGULAR: {
254
theNewParams->ViewingMode = StViewSurface_Sphere;
255
+ if(sizeX() == sizeY()) {
256
+ // TODO - hemisphere information should be somewhere in the file
257
+ //theNewParams->ViewingMode = StViewSurface_Hemisphere;
258
+ }
259
break;
260
}
261
case AV_SPHERICAL_CUBEMAP: {
262
263
//spherical->padding
264
break;
265
}
266
+ //case AV_SPHERICAL_MESH: { theNewParams->ViewingMode = StViewSurface_CubemapEAC; break; }
267
case AV_SPHERICAL_EQUIRECTANGULAR_TILE: {
268
// unsupported
269
//av_spherical_tile_bounds(aSpherical, par->width, par->height, &l, &t, &r, &b);
270
271
#endif
272
273
// stereoscopic mode tags
274
- myStFormatInStream = is720in1080 ? StFormat_Tiled4x : StFormat_AUTO;
275
+ myStFormatInStream = check720in1080() ? StFormat_Tiled4x : StFormat_AUTO;
276
if(stAV::meta::readTag(myFormatCtx, THE_SRC_MODE_KEY, aValue)
277
|| stAV::meta::readTag(myStream, THE_SRC_MODE_KEY, aValue)
278
|| stAV::meta::readTag(myFormatCtx, THE_SRC_MODE_KEY_WMV, aValue)) {
279
280
281
// detect information from file name
282
bool isAnamorphByName = false;
283
- myStFormatByName = st::formatFromName(myFileName, isAnamorphByName);
284
+ myStFormatByName = st::formatFromName(myFileName, myToSwapJps, isAnamorphByName);
285
if(myStFormatInStream == StFormat_AUTO
286
&& isAnamorphByName) {
287
if(myStFormatByName == StFormat_SideBySide_LR
288
289
myFramesCounter = 1;
290
myCachedFrame.nullify();
291
292
- if(myCodecCtx != NULL
293
- && myCodecAuto != NULL) {
294
- myCodecCtx->codec_id = myCodecAuto->id;
295
- }
296
+#if !defined(ST_AV_NEWCODECPAR)
297
+ if(myCodecCtx != NULL) { myCodecCtx->codec_id = myCodecAutoId; }
298
+#endif
299
StAVPacketQueue::deinit();
300
+ if(!myHWAccelCtx.isNull()) {
301
+ myHWAccelCtx->decoderDestroy(myCodecCtx);
302
+ }
303
if(myCodecCtx != NULL) {
304
myCodecCtx->hwaccel_context = NULL;
305
}
306
- if(!myHWAccelCtx.isNull()) {
307
- myHWAccelCtx->decoderDestroy();
308
- }
309
}
310
311
#ifdef ST_AV_OLDSYNC
312
313
stAV::dimYUV aDimsYUV;
314
myFrame.getImageInfo(myCodecCtx, aFrameSizeX, aFrameSizeY, aPixFmt);
315
myDataAdp.setBufferCounter(NULL);
316
- if(aPixFmt == stAV::PIX_FMT::XYZ12) {
317
+ if(aPixFmt == stAV::PIX_FMT::XYZ12
318
+ && myTextureQueue->getDeviceCaps().isSupportedFormat(StImagePlane::ImgRGB48)) {
319
myDataAdp.setColorModel(StImage::ImgColor_XYZ);
320
myDataAdp.setColorScale(StImage::ImgScale_Full);
321
myDataAdp.setPixelRatio(getPixelRatio());
322
myDataAdp.changePlane(0).initWrapper(StImagePlane::ImgRGB48, myFrame.getPlane(0),
323
size_t(aFrameSizeX), size_t(aFrameSizeY),
324
myFrame.getLineSize(0));
325
- } else if(aPixFmt == stAV::PIX_FMT::RGB24) {
326
+ return;
327
+ } else if(aPixFmt == stAV::PIX_FMT::RGB24
328
+ && myTextureQueue->getDeviceCaps().isSupportedFormat(StImagePlane::ImgRGB)) {
329
myDataAdp.setColorModel(StImage::ImgColor_RGB);
330
myDataAdp.setColorScale(StImage::ImgScale_Full);
331
myDataAdp.setPixelRatio(getPixelRatio());
332
myDataAdp.changePlane(0).initWrapper(StImagePlane::ImgRGB, myFrame.getPlane(0),
333
size_t(aFrameSizeX), size_t(aFrameSizeY),
334
myFrame.getLineSize(0));
335
+ return;
336
+ } else if(aPixFmt == stAV::PIX_FMT::RGBA32
337
+ && myTextureQueue->getDeviceCaps().isSupportedFormat(StImagePlane::ImgRGBA)) {
338
+ myDataAdp.setColorModel(StImage::ImgColor_RGBA);
339
+ myDataAdp.setColorScale(StImage::ImgScale_Full);
340
+ myDataAdp.setPixelRatio(getPixelRatio());
341
+ myDataAdp.changePlane(0).initWrapper(StImagePlane::ImgRGBA, myFrame.getPlane(0),
342
+ size_t(aFrameSizeX), size_t(aFrameSizeY),
343
+ myFrame.getLineSize(0));
344
+ return;
345
#if(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(53, 5, 0))
346
} else if(stAV::isFormatYUVPlanar(myFrame.Frame,
347
#else
348
349
} else if(aDimsYUV.bitsPerComp == 16) {
350
aPlaneFrmt = StImagePlane::ImgGray16;
351
}
352
- myDataAdp.setColorModel(StImage::ImgColor_YUV);
353
- myDataAdp.setPixelRatio(getPixelRatio());
354
- myDataAdp.changePlane(0).initWrapper(aPlaneFrmt, myFrame.getPlane(0),
355
- size_t(aDimsYUV.widthY), size_t(aDimsYUV.heightY), myFrame.getLineSize(0));
356
- myDataAdp.changePlane(1).initWrapper(aPlaneFrmt, myFrame.getPlane(1),
357
- size_t(aDimsYUV.widthU), size_t(aDimsYUV.heightU), myFrame.getLineSize(1));
358
- myDataAdp.changePlane(2).initWrapper(aPlaneFrmt, myFrame.getPlane(2),
359
- size_t(aDimsYUV.widthV), size_t(aDimsYUV.heightV), myFrame.getLineSize(2));
360
361
- myFrameBufRef->moveReferenceFrom(myFrame.Frame);
362
- myDataAdp.setBufferCounter(myFrameBufRef);
363
+ if(myTextureQueue->getDeviceCaps().isSupportedFormat(aPlaneFrmt)) {
364
+ myDataAdp.setColorModel(aDimsYUV.hasAlpha ? StImage::ImgColor_YUVA : StImage::ImgColor_YUV);
365
+ myDataAdp.setPixelRatio(getPixelRatio());
366
+ myDataAdp.changePlane(0).initWrapper(aPlaneFrmt, myFrame.getPlane(0),
367
+ size_t(aDimsYUV.widthY), size_t(aDimsYUV.heightY), myFrame.getLineSize(0));
368
+ myDataAdp.changePlane(1).initWrapper(aPlaneFrmt, myFrame.getPlane(1),
369
+ size_t(aDimsYUV.widthU), size_t(aDimsYUV.heightU), myFrame.getLineSize(1));
370
+ myDataAdp.changePlane(2).initWrapper(aPlaneFrmt, myFrame.getPlane(2),
371
+ size_t(aDimsYUV.widthV), size_t(aDimsYUV.heightV), myFrame.getLineSize(2));
372
+ if(aDimsYUV.hasAlpha) {
373
+ myDataAdp.changePlane(3).initWrapper(aPlaneFrmt, myFrame.getPlane(3),
374
+ size_t(aDimsYUV.widthY), size_t(aDimsYUV.heightY), myFrame.getLineSize(3));
375
+ }
376
+
377
+ myFrameBufRef->moveReferenceFrom(myFrame.Frame);
378
+ myDataAdp.setBufferCounter(myFrameBufRef);
379
+ return;
380
+ }
381
} else if(aPixFmt == stAV::PIX_FMT::NV12) {
382
aDimsYUV.isFullScale = false;
383
#if(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(52, 29, 0))
384
385
386
myFrameBufRef->moveReferenceFrom(myFrame.Frame);
387
myDataAdp.setBufferCounter(myFrameBufRef);
388
- } else if(!myToRgbIsBroken) {
389
+ return;
390
+ }
391
+
392
+ if(!myToRgbIsBroken) {
393
if(myToRgbCtx == NULL
394
|| myToRgbPixFmt != aPixFmt
395
|| size_t(aFrameSizeX) != myDataRGB.getSizeX()
396
397
signals.onError(stCString("FFmpeg: Failed to create SWScaler context"));
398
myToRgbIsBroken = true;
399
} else {
400
- // assign appropriate parts of RGB buffer to image planes in myFrameRGB
401
- const size_t aBufferSize = avpicture_get_size(stAV::PIX_FMT::RGB24, aFrameSizeX, aFrameSizeY);
402
- if(aBufferSize == 0
403
- || !myDataRGB.initTrash(StImagePlane::ImgRGB, size_t(aFrameSizeX), size_t(aFrameSizeY),
404
- aBufferSize / size_t(aFrameSizeY))) {
405
+ if(!myDataRGB.initTrash(StImagePlane::ImgRGB, size_t(aFrameSizeX), size_t(aFrameSizeY))) {
406
signals.onError(stCString("FFmpeg: Failed allocation of RGB frame (out of memory)"));
407
myToRgbIsBroken = true;
408
} else {
409
- avpicture_fill((AVPicture* )myFrameRGB.Frame, myDataRGB.changeData(), stAV::PIX_FMT::RGB24,
410
- aFrameSizeX, aFrameSizeY);
411
+ ST_DEBUG_LOG(" !!! Performance warning! Using SWScaler for " + stAV::PIX_FMT::getString(aPixFmt) + " pixel format.");
412
+ {
413
+ StMutexAuto aLock(myMutexInfo);
414
+ myCodecStr += StString("\n[SWScaler] Software converter (from ") + stAV::PIX_FMT::getString(aPixFmt) + stCString(" into RGB)");
415
+ }
416
+
417
+ myFrameRGB.Frame->data[0] = (uint8_t* )myDataRGB.changeData();
418
+ myFrameRGB.Frame->linesize[0] = (int )myDataRGB.getSizeRowBytes();
419
+ for(int aPlaneIter = 1; aPlaneIter < AV_NUM_DATA_POINTERS; ++aPlaneIter) {
420
+ myFrameRGB.Frame->data [aPlaneIter] = NULL;
421
+ myFrameRGB.Frame->linesize[aPlaneIter] = 0;
422
+ }
423
}
424
}
425
}
426
427
StPanorama aPano = st::probePanorama(theSrcFormat,
428
theStParams->Src1SizeX, theStParams->Src1SizeY,
429
theStParams->Src2SizeX, theStParams->Src2SizeY);
430
- theStParams->ViewingMode = (aPano == StPanorama_Cubemap6_1 || aPano == StPanorama_Cubemap3_2)
431
- ? StViewSurface_Cubemap
432
- : StViewSurface_Sphere;
433
+ theStParams->ViewingMode = StStereoParams::getViewSurfaceForPanoramaSource(aPano, true);
434
+ }
435
+ if(myIsTheaterMode && theStParams->ViewingMode == StViewSurface_Plain) {
436
+ theStParams->ViewingMode = StViewSurface_Theater;
437
+ } else if(!myIsTheaterMode && theStParams->ViewingMode == StViewSurface_Theater) {
438
+ theStParams->ViewingMode = StViewSurface_Plain;
439
}
440
441
myTextureQueue->push(theSrcDataLeft, theSrcDataRight, theStParams, theSrcFormat, theCubemapFormat, theSrcPTS);
442
443
}
444
445
void StVideoQueue::decodeLoop() {
446
- int isFrameFinished = 0;
447
double anAverageDelaySec = 40.0;
448
double aPrevPts = 0.0;
449
- double aSlavePts = 0.0;
450
myFramePts = 0.0;
451
- StImage* aSlaveData = NULL;
452
StHandle<StAVPacket> aPacket;
453
- StImage anEmptyImg;
454
StString aTagValue;
455
bool isStarted = false;
456
for(;;) {
457
458
myVideoClock = 0.0;
459
myHasDataState.reset();
460
isStarted = true;
461
+ aPrevPts = 0.0;
462
+ myWasFlushed = true; // force displaying the first frame
463
+ continue;
464
+ }
465
+ case StAVPacket::DATA_PACKET: {
466
+ break;
467
+ }
468
+ case StAVPacket::LAST_PACKET: {
469
+ #if(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(57, 106, 102))
470
+ break; // redirect NULL packet to avcodec_send_packet()break;
471
+ #else
472
continue;
473
+ #endif
474
}
475
case StAVPacket::END_PACKET: {
476
+ // TODO at the end of the stream it might be needed calling
477
+ // avcodec_send_packet with NULL to initiate draining data followed by avcodec_receive_frame
478
+ // to recieve last frames.
479
+
480
if(!myMaster.isNull()) {
481
while(myHasDataState.check() && !myMaster->isInDowntime()) {
482
StThread::sleep(10);
483
484
//
485
}
486
487
- // decode video frame
488
- #if(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(52, 23, 0))
489
- bool toTryGpu = myUseGpu && !myIsGpuFailed;
490
- avcodec_decode_video2(myCodecCtx, myFrame.Frame, &isFrameFinished, aPacket->getAVpkt());
491
- bool isGpuUsed = myUseGpu && !myIsGpuFailed;
492
- if(isGpuUsed != toTryGpu) {
493
- if(!initCodec(myCodecAuto, isGpuUsed)) {
494
- signals.onError(stCString("FFmpeg: Could not re-open video codec"));
495
- deinit();
496
- aPacket.nullify();
497
- continue;
498
+ bool toSendPacket = true;
499
+ for(;;) {
500
+ if(!decodeFrame(aPacket, toSendPacket, isStarted, aTagValue, anAverageDelaySec, aPrevPts)) {
501
+ break;
502
}
503
- isFrameFinished = 0;
504
- avcodec_decode_video2(myCodecCtx, myFrame.Frame, &isFrameFinished, aPacket->getAVpkt());
505
}
506
- #else
507
- avcodec_decode_video(myCodecCtx, myFrame.Frame, &isFrameFinished,
508
- aPacket->getData(), aPacket->getSize());
509
- #endif
510
- if(isFrameFinished == 0) {
511
- // need more packets to decode whole frame
512
- aPacket.nullify();
513
- continue;
514
+ aPacket.nullify();
515
+ }
516
+}
517
+
518
+bool StVideoQueue::decodeFrame(const StHandle<StAVPacket>& thePacket,
519
+ bool& theToSendPacket,
520
+ bool& theIsStarted,
521
+ StString& theTagValue,
522
+ double& theAverageDelaySec,
523
+ double& thePrevPts) {
524
+ bool toTryMoreFrames = false;
525
+ (void )theToSendPacket;
526
+ const bool toTryGpu = myUseGpu && !myIsGpuFailed;
527
+#if(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(57, 106, 102))
528
+ if(theToSendPacket) {
529
+ theToSendPacket = false;
530
+ const int aRes = avcodec_send_packet(myCodecCtx, thePacket->getType() == StAVPacket::DATA_PACKET ? thePacket->getAVpkt() : NULL);
531
+ if(aRes == AVERROR(EAGAIN)) {
532
+ // special case used by some hardware decoders - new packet cannot be sent until decoded frame is retrieved
533
+ theToSendPacket = true;
534
+ } else if(aRes < 0 && aRes != AVERROR_EOF) {
535
+ return false;
536
}
537
+ }
538
539
- if(aPacket->isKeyFrame()) {
540
- myFramesCounter = 1;
541
+ const int aRes2 = avcodec_receive_frame(myCodecCtx, myFrame.Frame);
542
+ const bool isGpuUsed = myUseGpu && !myIsGpuFailed;
543
+ if(isGpuUsed != toTryGpu) {
544
+ if(!initCodec(myCodecAuto, isGpuUsed)) {
545
+ signals.onError(stCString("FFmpeg: Could not re-open video codec"));
546
+ deinit();
547
+ return false;
548
}
549
+ theToSendPacket = true;
550
+ return true;
551
+ }
552
553
- #ifndef ST_AV_OLDSYNC
554
- myVideoPktPts = av_frame_get_best_effort_timestamp(myFrame.Frame);
555
- if(myVideoPktPts == stAV::NOPTS_VALUE) {
556
- myVideoPktPts = 0;
557
+ if(aRes2 < 0) {
558
+ // polling - if packet was not sent and new frame is not yet ready, we need to try again and again...
559
+ if(theToSendPacket) {
560
+ StThread::sleep(10);
561
+ }
562
+ return theToSendPacket;
563
+ }
564
+ toTryMoreFrames = true;
565
+#elif(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(52, 23, 0))
566
+ int isFrameFinished = 0;
567
+ avcodec_decode_video2(myCodecCtx, myFrame.Frame, &isFrameFinished, thePacket->getAVpkt());
568
+ const bool isGpuUsed = myUseGpu && !myIsGpuFailed;
569
+ if(isGpuUsed != toTryGpu) {
570
+ if(!initCodec(myCodecAuto, isGpuUsed)) {
571
+ signals.onError(stCString("FFmpeg: Could not re-open video codec"));
572
+ deinit();
573
+ return false;
574
}
575
+ return true;
576
+ }
577
+ if(isFrameFinished == 0) {
578
+ // need more packets to decode whole frame
579
+ return false;
580
+ }
581
+#else
582
+ int isFrameFinished = 0;
583
+ avcodec_decode_video(myCodecCtx, myFrame.Frame, &isFrameFinished,
584
+ thePacket->getData(), thePacket->getSize());
585
+ if(isFrameFinished == 0) {
586
+ // need more packets to decode whole frame
587
+ return false;
588
+ }
589
+#endif
590
+ if(thePacket->isKeyFrame()) { // !theToSentPacket?
591
+ myFramesCounter = 1;
592
+ }
593
594
- myFramePts = double(myVideoPktPts) * av_q2d(myStream->time_base);
595
- myFramePts -= myPtsStartBase; // normalize PTS
596
- #else
597
- // Save global pts to be stored in pFrame in first call
598
- myVideoPktPts = aPacket->getPts();
599
+#ifndef ST_AV_OLDSYNC
600
+ myVideoPktPts = myFrame.getBestEffortTimestamp();
601
+ if(myVideoPktPts == stAV::NOPTS_VALUE) {
602
+ // TODO why best_effort_timestamp is invalid in case of h264_mediacodec?
603
+ myVideoPktPts = myFrame.Frame->pts;
604
+ }
605
+ if(myVideoPktPts == stAV::NOPTS_VALUE) {
606
+ myVideoPktPts = 0;
607
+ }
608
609
- myFramePts = 0.0;
610
- if(aPacket->getDts() != stAV::NOPTS_VALUE) {
611
- myFramePts = double(aPacket->getDts());
612
- } else {
613
- int64_t aPktPtsSync = stAV::NOPTS_VALUE;
614
- #ifdef ST_USE64PTR
615
- aPktPtsSync = (int64_t )myFrame.Frame->opaque;
616
- #else
617
- AVFrameSideData* aSideDataSync = av_frame_get_side_data(myFrame.Frame, (AVFrameSideDataType )1000);
618
- if(aSideDataSync != NULL) {
619
- memcpy(&aPktPtsSync, &aSideDataSync->data, sizeof(myVideoPktPts));
620
- }
621
- #endif
622
- if(aPktPtsSync != stAV::NOPTS_VALUE) {
623
- myFramePts = double(aPktPtsSync);
624
- }
625
- }
626
- myFramePts *= av_q2d(myStream->time_base);
627
- myFramePts -= myPtsStartBase; // normalize PTS
628
+ myFramePts = double(myVideoPktPts) * av_q2d(myStream->time_base);
629
+ myFramePts -= myPtsStartBase; // normalize PTS
630
+#else
631
+ // Save global pts to be stored in pFrame in first call
632
+ myVideoPktPts = thePacket->getPts();
633
634
- syncVideo(myFrame.Frame, &myFramePts);
635
+ myFramePts = 0.0;
636
+ if(thePacket->getDts() != stAV::NOPTS_VALUE) {
637
+ myFramePts = double(thePacket->getDts());
638
+ } else {
639
+ int64_t aPktPtsSync = stAV::NOPTS_VALUE;
640
+ #ifdef ST_USE64PTR
641
+ aPktPtsSync = (int64_t )myFrame.Frame->opaque;
642
+ #else
643
+ AVFrameSideData* aSideDataSync = av_frame_get_side_data(myFrame.Frame, (AVFrameSideDataType )1000);
644
+ if(aSideDataSync != NULL) {
645
+ memcpy(&aPktPtsSync, &aSideDataSync->data, sizeof(myVideoPktPts));
646
+ }
647
#endif
648
-
649
- const double aDelay = myFramePts - aPrevPts;
650
- if(aDelay > 0.0 && aDelay < 1.0) {
651
- anAverageDelaySec = aDelay;
652
+ if(aPktPtsSync != stAV::NOPTS_VALUE) {
653
+ myFramePts = double(aPktPtsSync);
654
}
655
- aPrevPts = myFramePts;
656
-
657
- // do we need to skip frames or not
658
- static const double OVERR_LIMIT = 0.2;
659
- static const double GREATER_LIMIT = 100.0;
660
- if(myMaster.isNull()) {
661
- const double anAudioClock = getAClock() + double(myAudioDelayMSec) * 0.001;
662
- double diff = anAudioClock - myFramePts;
663
- if(diff > OVERR_LIMIT && diff < GREATER_LIMIT) {
664
- if(myAvDiscard != AVDISCARD_NONREF) {
665
- ST_DEBUG_LOG("skip frames: AVDISCARD_NONREF (on)"
666
- + " (aClock " + anAudioClock
667
- + " vClock " + myFramePts
668
- + " diff " + diff + ")"
669
- );
670
- myAvDiscard = AVDISCARD_NONREF;
671
- ///myCodecCtx->skip_frame = AVDISCARD_NONKEY;
672
- myCodecCtx->skip_frame = myAvDiscard;
673
- if(!mySlave.isNull()) {
674
- mySlave->myCodecCtx->skip_frame = myAvDiscard;
675
- }
676
+ }
677
+ myFramePts *= av_q2d(myStream->time_base);
678
+ myFramePts -= myPtsStartBase; // normalize PTS
679
+
680
+ syncVideo(myFrame.Frame, &myFramePts);
681
+#endif
682
+
683
+ const double aDelay = myFramePts - thePrevPts;
684
+ if(aDelay > 0.0 && aDelay < 1.0) {
685
+ theAverageDelaySec = aDelay;
686
+ }
687
+ thePrevPts = myFramePts;
688
+
689
+ // do we need to skip frames or not
690
+ static const double OVERR_LIMIT = 0.2;
691
+ static const double GREATER_LIMIT = 100.0;
692
+ if(myMaster.isNull()) {
693
+ const double anAudioClock = getAClock() + double(myAudioDelayMSec) * 0.001;
694
+ double diff = anAudioClock - myFramePts;
695
+ if(diff > OVERR_LIMIT && diff < GREATER_LIMIT) {
696
+ if(myAvDiscard != AVDISCARD_NONREF) {
697
+ ST_DEBUG_LOG("skip frames: AVDISCARD_NONREF (on)"
698
+ + " (aClock " + anAudioClock
699
+ + " vClock " + myFramePts
700
+ + " diff " + diff + ")"
701
+ );
702
+ myAvDiscard = AVDISCARD_NONREF;
703
+ ///myCodecCtx->skip_frame = AVDISCARD_NONKEY;
704
+ myCodecCtx->skip_frame = myAvDiscard;
705
+ if(!mySlave.isNull()) {
706
+ mySlave->myCodecCtx->skip_frame = myAvDiscard;
707
}
708
- } else {
709
- if(myAvDiscard != AVDISCARD_DEFAULT) {
710
- ST_DEBUG_LOG("skip frames: AVDISCARD_DEFAULT (off)");
711
- myAvDiscard = AVDISCARD_DEFAULT;
712
- myCodecCtx->skip_frame = myAvDiscard;
713
- if(!mySlave.isNull()) {
714
- mySlave->myCodecCtx->skip_frame = myAvDiscard;
715
- }
716
+ }
717
+ } else {
718
+ if(myAvDiscard != AVDISCARD_DEFAULT) {
719
+ ST_DEBUG_LOG("skip frames: AVDISCARD_DEFAULT (off)");
720
+ myAvDiscard = AVDISCARD_DEFAULT;
721
+ myCodecCtx->skip_frame = myAvDiscard;
722
+ if(!mySlave.isNull()) {
723
+ mySlave->myCodecCtx->skip_frame = myAvDiscard;
724
}
725
}
726
}
727
+ }
728
729
- // copy frame back from GPU to CPU memory
730
- if(!myHWAccelCtx.isNull()) {
731
- myHWAccelCtx->retrieveFrame(*this, myFrame.Frame);
732
- }
733
+ // copy frame back from GPU to CPU memory
734
+ if(!myHWAccelCtx.isNull()) {
735
+ myHWAccelCtx->retrieveFrame(*this, myFrame.Frame);
736
+ }
737
738
- // we currently allow to override source format stored in metadata
739
- #ifdef ST_AV_NEWSTEREO
740
- if(AVFrameSideData* aSideDataS3d = av_frame_get_side_data(myFrame.Frame, AV_FRAME_DATA_STEREO3D)) {
741
- AVStereo3D* aStereo = (AVStereo3D* )aSideDataS3d->data;
742
- myStFormatInStream = stAV::stereo3dAvToSt(aStereo->type);
743
- if(aStereo->flags & AV_STEREO3D_FLAG_INVERT) {
744
- myStFormatInStream = st::formatReversed(myStFormatInStream);
745
- }
746
+ // we currently allow to override source format stored in metadata
747
+#ifdef ST_AV_NEWSTEREO
748
+ if(AVFrameSideData* aSideDataS3d = av_frame_get_side_data(myFrame.Frame, AV_FRAME_DATA_STEREO3D)) {
749
+ AVStereo3D* aStereo = (AVStereo3D* )aSideDataS3d->data;
750
+ myStFormatInStream = stAV::stereo3dAvToSt(aStereo->type);
751
+ if(aStereo->flags & AV_STEREO3D_FLAG_INVERT) {
752
+ myStFormatInStream = st::formatReversed(myStFormatInStream);
753
}
754
- #endif
755
- #if(LIBAVUTIL_VERSION_INT >= AV_VERSION_INT(55, 0, 0))
756
- if(const AVFrameSideData* aSideDataRot = av_frame_get_side_data(myFrame.Frame, AV_FRAME_DATA_DISPLAYMATRIX)) {
757
- if(aSideDataRot->size >= int(9 * sizeof(int32_t))) {
758
- const double aRotDeg = -av_display_rotation_get((const int32_t* )aSideDataRot->data);
759
- if(!st::isNaN(aRotDeg)) {
760
- myRotateDeg = -int(aRotDeg - 360 * std::floor(aRotDeg / 360 + 0.9 / 360));
761
- }
762
+ }
763
+#endif
764
+#if(LIBAVUTIL_VERSION_INT >= AV_VERSION_INT(55, 0, 0))
765
+ if(const AVFrameSideData* aSideDataRot = av_frame_get_side_data(myFrame.Frame, AV_FRAME_DATA_DISPLAYMATRIX)) {
766
+ if(aSideDataRot->size >= int(9 * sizeof(int32_t))) {
767
+ const double aRotDeg = -av_display_rotation_get((const int32_t* )aSideDataRot->data);
768
+ if(!st::isNaN(aRotDeg)) {
769
+ myRotateDeg = -int(aRotDeg - 360 * std::floor(aRotDeg / 360 + 0.9 / 360));
770
}
771
}
772
- #endif
773
- if(stAV::meta::readTag(myFrame.Frame, THE_SRC_MODE_KEY, aTagValue)) {
774
- for(size_t aSrcId = 0;; ++aSrcId) {
775
- const StFFmpegStereoFormat& aFlag = STEREOFLAGS[aSrcId];
776
- if(aFlag.stID == StFormat_AUTO || aFlag.name == NULL) {
777
- break;
778
- } else if(aTagValue == aFlag.name) {
779
- myStFormatInStream = aFlag.stID;
780
- //ST_DEBUG_LOG(" read srcFormat from tags= " + myStFormatInStream);
781
- break;
782
- }
783
+ }
784
+#endif
785
+ if(stAV::meta::readTag(myFrame.Frame, THE_SRC_MODE_KEY, theTagValue)) {
786
+ for(size_t aSrcId = 0;; ++aSrcId) {
787
+ const StFFmpegStereoFormat& aFlag = STEREOFLAGS[aSrcId];
788
+ if(aFlag.stID == StFormat_AUTO || aFlag.name == NULL) {
789
+ break;
790
+ } else if(theTagValue == aFlag.name) {
791
+ myStFormatInStream = aFlag.stID;
792
+ //ST_DEBUG_LOG(" read srcFormat from tags= " + myStFormatInStream);
793
+ break;
794
}
795
}
796
- // override source format stored in metadata
797
- StFormat aSrcFormat = myStFormatByUser;
798
- StCubemap aCubemapFormat = aPacket->getSource()->ViewingMode == StViewSurface_Cubemap ? StCubemap_Packed : StCubemap_OFF;
799
- if(aSrcFormat == StFormat_AUTO) {
800
- // prefer info stored in the stream itself
801
- aSrcFormat = myStFormatInStream;
802
- }
803
- if(aSrcFormat == StFormat_AUTO) {
804
- // try using format detected from file name
805
- aSrcFormat = myStFormatByName;
806
- }
807
- /*if(aSrcFormat == StFormat_AUTO
808
- && sizeY() != 0) {
809
- // try detection based on aspect ratio
810
- aSrcFormat = st::formatFromRatio(GLfloat(sizeX()) / GLfloat(sizeY()));
811
- }*/
812
-
813
- prepareFrame(aSrcFormat);
814
+ }
815
+ // override source format stored in metadata
816
+ StFormat aSrcFormat = myStFormatByUser;
817
+ StCubemap aCubemapFormat = StCubemap_OFF;
818
+ if(thePacket->getSource()->ViewingMode == StViewSurface_Cubemap) {
819
+ aCubemapFormat = StCubemap_Packed;
820
+ } else if(thePacket->getSource()->ViewingMode == StViewSurface_CubemapEAC) {
821
+ aCubemapFormat = StCubemap_PackedEAC;
822
+ }
823
824
- if(!mySlave.isNull()) {
825
- if(isStarted) {
826
- StHandle<StStereoParams> aParams = aPacket->getSource();
827
- if(!aParams.isNull()) {
828
- aParams->setSeparationNeutral(myHParallax);
829
- aParams->setZRotateZero((float )myRotateDeg);
830
- }
831
- isStarted = false;
832
+ if(aSrcFormat == StFormat_AUTO) {
833
+ // prefer info stored in the stream itself
834
+ aSrcFormat = myStFormatInStream;
835
+ }
836
+ if(aSrcFormat == StFormat_AUTO) {
837
+ // try using format detected from file name
838
+ aSrcFormat = myStFormatByName;
839
+ }
840
+ /*if(aSrcFormat == StFormat_AUTO
841
+ && sizeY() != 0) {
842
+ // try detection based on aspect ratio
843
+ aSrcFormat = st::formatFromRatio(GLfloat(sizeX()) / GLfloat(sizeY()));
844
+ }*/
845
+
846
+ prepareFrame(aSrcFormat);
847
+
848
+ if(!mySlave.isNull()) {
849
+ if(theIsStarted) {
850
+ StHandle<StStereoParams> aParams = thePacket->getSource();
851
+ if(!aParams.isNull()) {
852
+ aParams->setSeparationNeutral(myHParallax);
853
+ aParams->setZRotateZero((float )myRotateDeg);
854
}
855
+ theIsStarted = false;
856
+ }
857
858
- for(;;) {
859
- // wait data from Slave
860
- if(aSlaveData == NULL) {
861
- aSlaveData = mySlave->waitData(aSlavePts);
862
- }
863
- if(aSlaveData != NULL) {
864
- const double aPtsDiff = myFramePts - aSlavePts;
865
- if(aPtsDiff > 0.5 * anAverageDelaySec) {
866
- // wait for more recent frame from slave thread
867
+ StImage* aSlaveData = NULL;
868
+ double aSlavePts = 0.0;
869
+ for(;;) {
870
+ // wait data from Slave
871
+ if(aSlaveData == NULL) {
872
+ aSlaveData = mySlave->waitData(aSlavePts);
873
+ }
874
+ if(aSlaveData != NULL) {
875
+ const double aPtsDiff = myFramePts - aSlavePts;
876
+ if(aPtsDiff > 0.5 * theAverageDelaySec) {
877
+ // wait for more recent frame from slave thread
878
+ mySlave->unlockData();
879
+ aSlaveData = NULL;
880
+ StThread::sleep(10);
881
+ continue;
882
+ } else if(aPtsDiff < -0.5 * theAverageDelaySec) {
883
+ // too far...
884
+ if(aPtsDiff < -6.0) {
885
+ // result of seeking?
886
mySlave->unlockData();
887
aSlaveData = NULL;
888
- StThread::sleep(10);
889
- continue;
890
- } else if(aPtsDiff < -0.5 * anAverageDelaySec) {
891
- // too far...
892
- if(aPtsDiff < -6.0) {
893
- // result of seeking?
894
- mySlave->unlockData();
895
- aSlaveData = NULL;
896
- }
897
- break;
898
}
899
+ break;
900
+ }
901
902
- pushFrame(myDataAdp, *aSlaveData, aPacket->getSource(), StFormat_SeparateFrames, aCubemapFormat, myFramePts);
903
+ pushFrame(myDataAdp, *aSlaveData, thePacket->getSource(), StFormat_SeparateFrames, aCubemapFormat, myFramePts);
904
905
- aSlaveData = NULL;
906
- mySlave->unlockData();
907
- } else {
908
- pushFrame(myDataAdp, anEmptyImg, aPacket->getSource(), aSrcFormat, aCubemapFormat, myFramePts);
909
- }
910
- break;
911
+ aSlaveData = NULL;
912
+ mySlave->unlockData();
913
+ } else {
914
+ pushFrame(myDataAdp, myEmptyImage, thePacket->getSource(), aSrcFormat, aCubemapFormat, myFramePts);
915
}
916
- } else if(!myMaster.isNull()) {
917
- // push data to Master
918
- myHasDataState.set();
919
- } else {
920
- if(isStarted) {
921
- StHandle<StStereoParams> aParams = aPacket->getSource();
922
- if(!aParams.isNull()) {
923
- aParams->setSeparationNeutral(myHParallax);
924
- aParams->setZRotateZero((float )myRotateDeg);
925
- }
926
- isStarted = false;
927
+ break;
928
+ }
929
+ } else if(!myMaster.isNull()) {
930
+ // push data to Master
931
+ myHasDataState.set();
932
+ } else {
933
+ if(theIsStarted) {
934
+ StHandle<StStereoParams> aParams = thePacket->getSource();
935
+ if(!aParams.isNull()) {
936
+ aParams->setSeparationNeutral(myHParallax);
937
+ aParams->setZRotateZero((float )myRotateDeg);
938
}
939
+ theIsStarted = false;
940
+ }
941
942
- // simple one-stream case
943
- if(aSrcFormat == StFormat_FrameSequence) {
944
- if(isOddNumber(myFramesCounter)) {
945
- myCachedFrame.fill(myDataAdp, false);
946
- } else {
947
- pushFrame(myCachedFrame, myDataAdp, aPacket->getSource(), StFormat_FrameSequence, aCubemapFormat, myFramePts);
948
- }
949
- ++myFramesCounter;
950
+ // simple one-stream case
951
+ if(aSrcFormat == StFormat_FrameSequence) {
952
+ if(isOddNumber(myFramesCounter)) {
953
+ myCachedFrame.fill(myDataAdp, false);
954
} else {
955
- pushFrame(myDataAdp, anEmptyImg, aPacket->getSource(), aSrcFormat, aCubemapFormat, myFramePts);
956
+ pushFrame(myCachedFrame, myDataAdp, thePacket->getSource(), StFormat_FrameSequence, aCubemapFormat, myFramePts);
957
}
958
+ ++myFramesCounter;
959
+ } else {
960
+ pushFrame(myDataAdp, myEmptyImage, thePacket->getSource(), aSrcFormat, aCubemapFormat, myFramePts);
961
}
962
-
963
- myFrame.reset();
964
- aPacket.nullify(); // and now packet finished
965
}
966
+
967
+ myFrame.reset();
968
+ return toTryMoreFrames;
969
}
970
sview-17_04.tar.gz/StMoviePlayer/StVideo/StVideoQueue.h -> sview-20_08.tar.gz/StMoviePlayer/StVideo/StVideoQueue.h
Changed
104
1
2
/**
3
- * Copyright © 2009-2017 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2009-2019 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* StMoviePlayer program is free software: you can redistribute it and/or modify
7
* it under the terms of the GNU General Public License as published by
8
9
/**
10
* Release decoder.
11
*/
12
- virtual void decoderDestroy() = 0;
13
+ virtual void decoderDestroy(AVCodecContext* theCodecCtx) = 0;
14
15
/**
16
* AVFrame initialization callback.
17
18
}
19
20
/**
21
+ * Set theater mode.
22
+ */
23
+ ST_LOCAL void setTheaterMode(bool theIsTheater) {
24
+ myIsTheaterMode = theIsTheater;
25
+ }
26
+
27
+ /**
28
* Stick to panorama 360 mode.
29
*/
30
ST_LOCAL void setStickPano360(bool theToStick) {
31
myToStickPano360 = theToStick;
32
}
33
34
+ /**
35
+ * Set if JPS file should be read as Left/Right (TRUE) of as Right/Left (FALSE).
36
+ */
37
+ ST_LOCAL void setSwapJPS(bool theToSwap) { myToSwapJps = theToSwap; }
38
+
39
ST_LOCAL StVideoQueue(const StHandle<StGLTextureQueue>& theTextureQueue,
40
const StHandle<StVideoQueue>& theMaster = StHandle<StVideoQueue>());
41
ST_LOCAL virtual ~StVideoQueue();
42
43
/**
44
+ * Return codec type.
45
+ */
46
+ ST_LOCAL virtual AVMediaType getCodecType() const ST_ATTR_OVERRIDE { return AVMEDIA_TYPE_VIDEO; }
47
+
48
+ /**
49
* Initialization function.
50
* @param theFormatCtx pointer to video format context
51
* @param theStreamId stream id in video format context
52
53
private:
54
55
/**
56
+ * Detect 720in1080 streams with cropping information
57
+ */
58
+ ST_LOCAL bool check720in1080() const {
59
+ return (sizeX() == 1280) && (sizeY() == 720)
60
+ && (getCodedSizeX() == 1920)
61
+ && (getCodedSizeY() == 1080 || getCodedSizeY() == 1088);
62
+ }
63
+
64
+ ST_LOCAL bool decodeFrame(const StHandle<StAVPacket>& thePacket,
65
+ bool& theToSendPacket,
66
+ bool& theIsStarted,
67
+ StString& theTagValue,
68
+ double& theAverageDelaySec,
69
+ double& thePrevPts);
70
+
71
+ /**
72
* Initialize adapter over AVframe or perform to RGB conversion.
73
*/
74
ST_LOCAL void prepareFrame(const StFormat theSrcFormat);
75
76
StHandle<StVideoQueue> mySlave; //!< handle to Slave decoding thread
77
78
StHandle<StHWAccelContext> myHWAccelCtx;
79
-#if defined(__APPLE__) || defined(__ANDROID__)
80
- AVCodec* myCodecH264HW; //!< h264 decoder using dedicated hardware (VDA codec on OS X; Android Media Codec)
81
+#if defined(__ANDROID__)
82
+ AVCodec* myCodecH264HW; //!< h264 decoder using dedicated hardware (Android Media Codec)
83
+ AVCodec* myCodecHevcHW; //!< hevc decoder using dedicated hardware
84
+ AVCodec* myCodecVp9HW; //!< vp9 decoder using dedicated hardware
85
#endif
86
AVCodec* myCodecOpenJpeg; //!< libopenjpeg decoder
87
bool myUseGpu; //!< activate decoding on GPU when possible
88
89
90
int64_t myFramesCounter;
91
StImage myCachedFrame;
92
+ StImage myEmptyImage;
93
bool myWasFlushed;
94
95
volatile StFormat myStFormatByUser; //!< source format specified by user
96
volatile StFormat myStFormatByName; //!< source format detected from file name
97
volatile StFormat myStFormatInStream;//!< source format information retrieved from stream
98
+ volatile bool myIsTheaterMode; //!< flag indicating theater mode
99
volatile bool myToStickPano360; //!< stick to panorama 360 mode
100
+ volatile bool myToSwapJps; //!< read JPS as Left/Right instead of Right/Left
101
102
};
103
104
sview-17_04.tar.gz/StMoviePlayer/StVideo/StVideoTimer.cpp -> sview-20_08.tar.gz/StMoviePlayer/StVideo/StVideoTimer.cpp
Changed
12
1
2
if(mySpeedSlow * myDelayTimer > myDelayVVAver) {
3
myDelayTimer = mySpeedSlowRev * myDelayVVAver;
4
} else if(mySpeedFastSkip * myDelayTimer < myDelayVVAver) {
5
- //myVideo->getTextureQueue()->drop(2);
6
- myVideo->getTextureQueue()->drop(1);
7
+ //myVideo->getTextureQueue()->drop(2, myVideoPtsNextSec);
8
+ myVideo->getTextureQueue()->drop(1, myVideoPtsNextSec);
9
myDelayTimer = mySpeedFastRev * myDelayVVAver;
10
} else if(mySpeedFast * myDelayTimer < myDelayVVAver) {
11
myDelayTimer = mySpeedFastRev * myDelayVVAver;
12
sview-20_08.tar.gz/StMoviePlayer/StVideo/StVideoToolbox.cpp
Added
250
1
2
+/**
3
+ * Copyright © 2020 Kirill Gavrilov <kirill@sview.ru>
4
+ *
5
+ * StMoviePlayer program is free software: you can redistribute it and/or modify
6
+ * it under the terms of the GNU General Public License as published by
7
+ * the Free Software Foundation, either version 3 of the License, or
8
+ * (at your option) any later version.
9
+ *
10
+ * StMoviePlayer program is distributed in the hope that it will be useful,
11
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
12
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
13
+ * See the GNU General Public License for more details.
14
+ *
15
+ * You should have received a copy of the GNU General Public
16
+ * License along with this program.
17
+ * If not, see <http://www.gnu.org/licenses/>.
18
+ */
19
+
20
+#include "StVideoQueue.h"
21
+
22
+#if defined(__APPLE__)
23
+
24
+#include <StAV/StAVPacket.h>
25
+#include <StAV/StAVFrame.h>
26
+#include <StAV/StAVBufferPool.h>
27
+#include <StLibrary.h>
28
+
29
+#include <vector>
30
+
31
+#include <CoreServices/CoreServices.h>
32
+
33
+extern "C" {
34
+ #include <libavcodec/videotoolbox.h>
35
+ #include <libavutil/buffer.h>
36
+ #include <libavutil/imgutils.h>
37
+};
38
+
39
+/**
40
+ * VideoToolbox HWAccel context.
41
+ */
42
+class StVideoToolboxContext : public StHWAccelContext {
43
+
44
+ public:
45
+
46
+ /**
47
+ * Empty constructor.
48
+ */
49
+ StVideoToolboxContext()
50
+ : myFrameTmp(NULL),
51
+ myHasDevice(false){
52
+ //
53
+ }
54
+
55
+ /**
56
+ * Destructor.
57
+ */
58
+ virtual ~StVideoToolboxContext() {
59
+ release();
60
+ }
61
+
62
+ /**
63
+ * Release context.
64
+ */
65
+ void release();
66
+
67
+ /**
68
+ * Return true if VideoToolbox has been successfully initialized.
69
+ */
70
+ virtual bool isValid() const ST_ATTR_OVERRIDE { return myHasDevice; }
71
+
72
+ /**
73
+ * Create context.
74
+ */
75
+ virtual bool create(StVideoQueue& theVideo) ST_ATTR_OVERRIDE;
76
+
77
+ /**
78
+ * Destroy decoder.
79
+ */
80
+ virtual void decoderDestroy(AVCodecContext* theCodecCtx) ST_ATTR_OVERRIDE {
81
+ myPoolsTmp[0].release();
82
+ myPoolsTmp[1].release();
83
+ myPoolsTmp[2].release();
84
+ myPoolsTmp[3].release();
85
+ if(theCodecCtx != NULL && myHasDevice) {
86
+ av_videotoolbox_default_free(theCodecCtx);
87
+ }
88
+ myHasDevice = false;
89
+ }
90
+
91
+ /**
92
+ * Create decoder.
93
+ */
94
+ virtual bool decoderCreate(StVideoQueue& theVideo,
95
+ AVCodecContext* theCodecCtx) ST_ATTR_OVERRIDE {
96
+ const StSignal<void (const StCString& )>& onError = theVideo.signals.onError;
97
+ decoderDestroy(theCodecCtx);
98
+
99
+ const int anAvErr = av_videotoolbox_default_init(theCodecCtx);
100
+ if(anAvErr < 0) {
101
+ onError(stCString("StVideoQueue: Error creating Videotoolbox decoder"));
102
+ return false;
103
+ }
104
+ myHasDevice = true;
105
+ return true;
106
+ }
107
+
108
+ /**
109
+ * AVFrame initialization callback.
110
+ */
111
+ virtual int getFrameBuffer(StVideoQueue& ,
112
+ AVFrame* ) ST_ATTR_OVERRIDE {
113
+ return -1; // method is unused
114
+ }
115
+
116
+ /**
117
+ * Fetch decoded results into specified frame.
118
+ */
119
+ virtual bool retrieveFrame(StVideoQueue& theVideo,
120
+ AVFrame* theFrame) ST_ATTR_OVERRIDE;
121
+
122
+ private:
123
+
124
+ StAVBufferPool myPoolsTmp[4];
125
+ AVFrame* myFrameTmp;
126
+ bool myHasDevice;
127
+
128
+};
129
+
130
+void StVideoToolboxContext::release() {
131
+ decoderDestroy(NULL);
132
+ av_frame_free(&myFrameTmp);
133
+}
134
+
135
+bool StVideoToolboxContext::create(StVideoQueue& ) {
136
+ myFrameTmp = av_frame_alloc();
137
+ if(myFrameTmp == NULL) {
138
+ release();
139
+ return false;
140
+ }
141
+ return true;
142
+}
143
+
144
+bool StVideoToolboxContext::retrieveFrame(StVideoQueue& ,
145
+ AVFrame* theFrame) {
146
+ if(!isValid()
147
+ || theFrame->format != stAV::PIX_FMT::VIDEOTOOLBOX_VLD) {
148
+ return false;
149
+ }
150
+
151
+ av_frame_unref(myFrameTmp);
152
+
153
+ CVPixelBufferRef aPixBuf = (CVPixelBufferRef )theFrame->data[3];
154
+ const OSType aPixBufFormat = CVPixelBufferGetPixelFormatType(aPixBuf);
155
+ switch(aPixBufFormat) {
156
+ case kCVPixelFormatType_420YpCbCr8Planar: myFrameTmp->format = AV_PIX_FMT_YUV420P; break;
157
+ case kCVPixelFormatType_422YpCbCr8: myFrameTmp->format = AV_PIX_FMT_UYVY422; break;
158
+ case kCVPixelFormatType_32BGRA: myFrameTmp->format = AV_PIX_FMT_BGRA; break;
159
+ case kCVPixelFormatType_420YpCbCr8BiPlanarVideoRange:
160
+ case kCVPixelFormatType_420YpCbCr8BiPlanarFullRange: myFrameTmp->format = AV_PIX_FMT_NV12; break;
161
+ case kCVPixelFormatType_420YpCbCr10BiPlanarVideoRange:
162
+ case kCVPixelFormatType_420YpCbCr10BiPlanarFullRange: myFrameTmp->format = AV_PIX_FMT_P010; break;
163
+ default: {
164
+ ST_ERROR_LOG("StVideoToolboxContext: unsupported pixel format " + int(aPixBufFormat));
165
+ return false;
166
+ }
167
+ }
168
+
169
+ CVReturn err = CVPixelBufferLockBaseAddress(aPixBuf, kCVPixelBufferLock_ReadOnly);
170
+ if(err != kCVReturnSuccess) {
171
+ ST_ERROR_LOG("StVideoToolboxContext: Error locking the pixel buffer");
172
+ return false;
173
+ }
174
+
175
+ myFrameTmp->width = theFrame->width;
176
+ myFrameTmp->height = theFrame->height;
177
+ size_t aDataSize[4] = { 0 };
178
+
179
+ uint8_t* aData[4] = { 0 };
180
+ int aLineSize[4] = { 0 };
181
+ const int aNbPlanes = CVPixelBufferIsPlanar(aPixBuf) ? CVPixelBufferGetPlaneCount(aPixBuf) : 1;
182
+ if(CVPixelBufferIsPlanar(aPixBuf)) {
183
+ for(int aPlaneIter = 0; aPlaneIter < aNbPlanes; ++aPlaneIter) {
184
+ aData[aPlaneIter] = (uint8_t* )CVPixelBufferGetBaseAddressOfPlane(aPixBuf, aPlaneIter);
185
+ aLineSize[aPlaneIter] = CVPixelBufferGetBytesPerRowOfPlane(aPixBuf, aPlaneIter);
186
+
187
+ const int aTmpStride = aLineSize[aPlaneIter]; //(int )getAligned(CVPixelBufferGetWidthOfPlane(aPixBuf, aPlaneIter) * bytesPerPixel, 32);
188
+ myFrameTmp->linesize[aPlaneIter] = aTmpStride;
189
+ aDataSize[aPlaneIter] = size_t(aTmpStride) * size_t(CVPixelBufferGetHeightOfPlane(aPixBuf, aPlaneIter));
190
+ }
191
+ } else {
192
+ aData[0] = (uint8_t* )CVPixelBufferGetBaseAddress(aPixBuf);
193
+ aLineSize[0] = CVPixelBufferGetBytesPerRow(aPixBuf);
194
+
195
+ const int aTmpStride = aLineSize[0]; //(int )getAligned(CVPixelBufferGetWidth(aPixBuf) * bytesPerPixel, 32);
196
+ myFrameTmp->linesize[0] = aTmpStride;
197
+ aDataSize[0] = size_t(aTmpStride) * size_t(CVPixelBufferGetHeight(aPixBuf));
198
+ }
199
+
200
+ for(int aPlaneIter = 0; aPlaneIter < aNbPlanes; ++aPlaneIter) {
201
+ myFrameTmp->buf[aPlaneIter] = myPoolsTmp[aPlaneIter].init(aDataSize[aPlaneIter]) ? myPoolsTmp[aPlaneIter].getBuffer() : NULL;
202
+ if(myFrameTmp->buf[aPlaneIter] == NULL) {
203
+ ST_ERROR_LOG("StVideoToolboxContext: unable to allocate frame buffers");
204
+ av_frame_unref(myFrameTmp);
205
+ CVPixelBufferUnlockBaseAddress(aPixBuf, kCVPixelBufferLock_ReadOnly);
206
+ return false;
207
+ }
208
+ myFrameTmp->data[aPlaneIter] = myFrameTmp->buf[aPlaneIter]->data;
209
+ }
210
+ //int anAvErrBuf = av_frame_get_buffer(myFrameTmp, 0);
211
+ //if(anAvErrBuf < 0) { return false; }
212
+
213
+ av_image_copy(myFrameTmp->data, myFrameTmp->linesize,
214
+ (const uint8_t** )aData, aLineSize, (AVPixelFormat )myFrameTmp->format,
215
+ theFrame->width, theFrame->height);
216
+
217
+ const int anAvErr = av_frame_copy_props(myFrameTmp, theFrame);
218
+ CVPixelBufferUnlockBaseAddress(aPixBuf, kCVPixelBufferLock_ReadOnly);
219
+ if(anAvErr < 0) {
220
+ ST_ERROR_LOG("StVideoToolboxContext: Error copying frame properties");
221
+ av_frame_unref(myFrameTmp);
222
+ return false;
223
+ }
224
+
225
+ av_frame_unref (theFrame);
226
+ av_frame_move_ref(theFrame, myFrameTmp);
227
+ return true;
228
+}
229
+
230
+bool StVideoQueue::hwaccelInit() {
231
+ if(myCodecCtx->codec_id == AV_CODEC_ID_NONE) {
232
+ return false;
233
+ }
234
+
235
+ if(myHWAccelCtx.isNull()) {
236
+ myHWAccelCtx = new StVideoToolboxContext();
237
+ if(!myHWAccelCtx->create(*this)) {
238
+ return false;
239
+ }
240
+ }
241
+
242
+ if(!myHWAccelCtx->decoderCreate(*this, myCodecCtx)) {
243
+ return false;
244
+ }
245
+ fillCodecInfo(myCodecCtx->codec, " (VideoToolbox)");
246
+ return true;
247
+}
248
+
249
+#endif // __APPLE__
250
sview-17_04.tar.gz/StMoviePlayer/lang/chinese/StMoviePlayer.lng -> sview-20_08.tar.gz/StMoviePlayer/lang/chinese/StMoviePlayer.lng
Changed
57
1
2
1260=接近
3
1261=线性
4
1262=混纺交织
5
+?1263=Trilinear
6
1270=重置默认
7
1271=亮度
8
1272=饱和度
9
10
1281=球面
11
1282=圆筒
12
?1283=Cubemap
13
+?1284=Hemisphere
14
?1285=Track orientation
15
?1286=Track orientation (poor)
16
?1287=Orient audio
17
?1288=Stick at panorama 360°
18
+?1293=Equiangular cubemap
19
+?1294=Theater
20
1300=音频
21
1301=无
22
1302=音/视频 延迟
23
24
?1359=Bottom
25
?1360=Plain text
26
?1361=Lite HTML
27
+?1370=Apply stereo format
28
1400=改变设备
29
1401=关于插件…
30
1402=FPS控制
31
+?1404=Exclusive Fullscreen mode
32
1420=同时
33
1421=显示表
34
1422=减少CPU的使用
35
36
?1705=On one click windowed mode
37
?1710=Hide system navigation bar
38
?1711=Open last played file on startup
39
+?1712=Swap JPS/PNS views order
40
2000=选择视频文件打开
41
2001=选择左视频文件打开
42
2002=选择右视频文件打开
43
44
2005=文件删除
45
2006=确定完全移除吗?
46
2007=激活解码器:
47
+?2008=Choose audio file to attach
48
+?2009=Choose subtitles file to attach
49
2010=选择保存快照位置
50
2011=什么也没有保存!
51
2012=快照不为空!
52
53
?6055=X Rotation - up
54
?6056=X Rotation - down
55
?6057=Enable/disable panorama mode
56
+?6058=Show/hide GUI
57
sview-17_04.tar.gz/StMoviePlayer/lang/czech/StMoviePlayer.lng -> sview-20_08.tar.gz/StMoviePlayer/lang/czech/StMoviePlayer.lng
Changed
57
1
2
1260=Nevyhlazovat
3
1261=Lineární
4
1262=Odstranit prokládání
5
+?1263=Trilinear
6
1270=Resetovat nastavení
7
1271=Jas
8
1272=Sytost
9
10
1281=Koule
11
1282=Válec
12
?1283=Cubemap
13
+?1284=Hemisphere
14
?1285=Track orientation
15
?1286=Track orientation (poor)
16
?1287=Orient audio
17
?1288=Stick at panorama 360°
18
+?1293=Equiangular cubemap
19
+?1294=Theater
20
1300=Zvuk
21
1301=Vypnout zvuk
22
1302=Zpoždění zvuku
23
24
?1359=Bottom
25
1360=Plain text
26
1361=Lite HTML
27
+?1370=Apply stereo format
28
1400=Vybrat zařízení
29
1401=O modulu…
30
1402=FPS nastavení
31
+?1404=Exclusive Fullscreen mode
32
1420=Vertikální synchronizace
33
1421=Zobrazovat snímkování (fps)
34
1422=Omezit využití CPU
35
36
?1705=On one click windowed mode
37
?1710=Hide system navigation bar
38
?1711=Open last played file on startup
39
+?1712=Swap JPS/PNS views order
40
2000=Otevřít video
41
2001=Otevřít video s LEVOU stopou
42
2002=Otevřít video s PRAVOU stopou
43
44
2005=Vymazat soubor
45
2006=Skutečně chcete hodit soubor do koše?
46
2007=Aktivní dekódery
47
+?2008=Choose audio file to attach
48
+?2009=Choose subtitles file to attach
49
2010=Zvolte místo pro uložení obrázku
50
2011=Nic není otevřeno!
51
2012=Obraz není možné uložit!
52
53
?6055=X Rotation - up
54
?6056=X Rotation - down
55
?6057=Enable/disable panorama mode
56
+?6058=Show/hide GUI
57
sview-17_04.tar.gz/StMoviePlayer/lang/english/StMoviePlayer.lng -> sview-20_08.tar.gz/StMoviePlayer/lang/english/StMoviePlayer.lng
Changed
57
1
2
1260=Nearest
3
1261=Linear
4
1262=Blend Deinterlace
5
+?1263=Trilinear
6
1270=Reset to defaults
7
1271=Brightness
8
1272=Saturation
9
10
1281=Sphere
11
1282=Cylinder
12
1283=Cubemap
13
+1284=Hemisphere
14
1285=Track orientation
15
1286=Track orientation (poor)
16
1287=Orient audio
17
1288=Stick at panorama 360°
18
+1293=Equiangular cubemap
19
+1294=Theater
20
1300=Audio
21
1301=None
22
1302=Audio/Video delay
23
24
1359=Bottom
25
1360=Plain text
26
1361=Lite HTML
27
+1370=Apply stereo format
28
1400=Change device
29
1401=About Plugin...
30
1402=FPS Control
31
+1404=Exclusive Fullscreen mode
32
1420=VSync
33
1421=Show Meter
34
1422=Reduce CPU usage
35
36
1705=On one click in windowed mode
37
1710=Hide system navigation bar
38
1711=Open last played file on startup
39
+1712=Swap JPS/PNS views order
40
2000=Choose the video file to open
41
2001=Choose LEFT video file to open
42
2002=Choose RIGHT video file to open
43
44
2005=File deletion
45
2006=Do you really want to completely remove this file?
46
2007=Active decoders:
47
+2008=Choose audio file to attach
48
+2009=Choose subtitles file to attach
49
2010=Choose location to save snapshot
50
2011=Nothing to save!
51
2012=Snapshot not available!
52
53
6055=X Rotation - up
54
6056=X Rotation - down
55
6057=Enable/disable panorama mode
56
+6058=Show/hide GUI
57
sview-17_04.tar.gz/StMoviePlayer/lang/french/StMoviePlayer.lng -> sview-20_08.tar.gz/StMoviePlayer/lang/french/StMoviePlayer.lng
Changed
57
1
2
1260=Plus proche
3
1261=Lineaire
4
1262=Blend Deinterlace
5
+1263=Trilinéaire
6
1270=Rétablir par défaut
7
1271=Brightness
8
1272=Saturation
9
10
1281=Sphère
11
1282=Cylindre
12
1283=Cubemap
13
+1284=Hémisphère
14
?1285=Track orientation
15
?1286=Track orientation (poor)
16
?1287=Orient audio
17
?1288=Stick at panorama 360°
18
+?1293=Equiangular cubemap
19
+1294=Théâtre
20
1300=Audio
21
1301=Aucun
22
1302=Audio/Video delay
23
24
1359=Au fond
25
?1360=Plain text
26
?1361=Lite HTML
27
+?1370=Apply stereo format
28
1400=Changer la sortie
29
1401=A propos du Plugin...
30
1402=Contrôle de I/S
31
+?1404=Exclusive Fullscreen mode
32
1420=Synchro Vert.
33
1421=Voir I/S
34
1422=Réduire l'utilisation de CPU
35
36
?1705=On one click windowed mode
37
?1710=Hide system navigation bar
38
?1711=Open last played file on startup
39
+1712=JPS/PNS échange de vues pour
40
2000=Choix du fichier vidéo à ouvrir
41
2001=Choix du fichier vidéo Gauche à ouvrir
42
2002=Choix du fichier vidéo Droite à ouvrir
43
44
?2005=File deletion
45
?2006=Do you really want to completely remove this file?
46
?2007=Active decoders:
47
+2008=Choix du fichier audio à joindre
48
+2009=Choix du fichier sous-titres à joindre
49
2010=Emplacement de la capture écran
50
2011=Rien à enregistrer!
51
2012=Capture non disponible!
52
53
?6055=X Rotation - up
54
?6056=X Rotation - down
55
6057=Activer / désactiver le mode panorama
56
+6058=Masquer l'interface
57
sview-17_04.tar.gz/StMoviePlayer/lang/german/StMoviePlayer.lng -> sview-20_08.tar.gz/StMoviePlayer/lang/german/StMoviePlayer.lng
Changed
57
1
2
1260=Nearest
3
1261=Linear
4
1262=Blend Deinterlace
5
+1263=Trilinear
6
1270=Auf Standardwerte zurücksetzen
7
1271=Helligkeit
8
1272=Sättigung
9
10
1281=Kugel
11
1282=Zylinder
12
1283=Cubemap
13
+1284=Hemisphäre
14
?1285=Track orientation
15
?1286=Track orientation (poor)
16
?1287=Orient audio
17
?1288=Stick at panorama 360°
18
+?1293=Equiangular cubemap
19
+1294=Theater
20
1300=Audio
21
1301=keiner
22
1302=Audio/Video Verzögerung
23
24
1359=Boden
25
1360=Plain text
26
1361=Lite HTML
27
+1370=Stereoformat anwenden
28
1400=Gerät ändern
29
1401=Über Plugin...
30
1402=FPS Kontrolle
31
+1404=Exklusiver Vollbildmodus
32
1420=VSync
33
1421=Zeige Meter
34
1422=Reduce CPU usage
35
36
?1705=Only when windowed
37
1710=Navigationsleiste ausblenden
38
?1711=Open last played file on startup
39
+1712=JPS/PNS-Ansichten, um zu tauschen
40
2000=Wählen die Videodatei zu öffnen
41
2001=Wählen die linke Videodatei zu öffnen
42
2002=Wählen die rechte Videodatei zu öffnen
43
44
2005=Löschen von Dateien
45
?2006=Do you really want to completely remove this file?
46
?2007=Active decoders:
47
+2008=Wählen die anzuhängende Audiodatei
48
+2009=Wählen die anzuhängende Untertiteldatei
49
2010=Wählen einen Speicherort für Videoschnappschuss
50
2011=Nichts zu speichern!
51
2012=Schnappschuss ist nicht verfügbar!
52
53
6055=X-Drehung - nach oben
54
6056=X-Drehung - nach unten
55
6057=Aktivieren / Deaktivieren der Panorama-Modus
56
+6058=GUI ausblenden
57
sview-17_04.tar.gz/StMoviePlayer/lang/korean/StMoviePlayer.lng -> sview-20_08.tar.gz/StMoviePlayer/lang/korean/StMoviePlayer.lng
Changed
57
1
2
?1260=Nearest
3
?1261=Linear
4
?1262=Blend Deinterlace
5
+?1263=Trilinear
6
1270=초기값 리셋
7
1271=밝기
8
?1272=Saturation
9
10
?1281=Sphere
11
?1282=Cylinder
12
?1283=Cubemap
13
+?1284=Hemisphere
14
?1285=Track orientation
15
?1286=Track orientation (poor)
16
?1287=Orient audio
17
?1288=Stick at panorama 360°
18
+?1293=Equiangular cubemap
19
+?1294=Theater
20
?1300=Audio
21
1301=없음
22
1302=오디오/비디오 지연시간
23
24
?1359=Bottom
25
?1360=Plain text
26
?1361=Lite HTML
27
+?1370=Apply stereo format
28
1400=장치 변경
29
?1401=About Plugin...
30
?1402=FPS 제어
31
+?1404=Exclusive Fullscreen mode
32
?1420=VSync
33
?1421=Show Meter
34
1422=CPU 부하 감소
35
36
?1705=On one click windowed mode
37
?1710=Hide system navigation bar
38
?1711=Open last played file on startup
39
+?1712=Swap JPS/PNS views order
40
2000=재생할 비디오 파일을 선택하시오
41
2001=좌안 비디오 파일을 선택하시오
42
2002=우안 비디오 파일을 선택하시오
43
44
?2005=File deletion
45
?2006=Do you really want to completely remove this file?
46
?2007=Active decoders:
47
+?2008=Choose audio file to attach
48
+?2009=Choose subtitles file to attach
49
2010=스냅샷을 저장할 위치를 선택하시오
50
2011=저장할 수 없음!
51
2012=스냅샷 없음!
52
53
?6055=X Rotation - up
54
?6056=X Rotation - down
55
?6057=Enable/disable panorama mode
56
+?6058=Show/hide GUI
57
sview-17_04.tar.gz/StMoviePlayer/lang/russian/StMoviePlayer.lng -> sview-20_08.tar.gz/StMoviePlayer/lang/russian/StMoviePlayer.lng
Changed
61
1
2
1260=Без сглаживания
3
1261=Линейное
4
1262=Blend Deinterlace
5
+1263=Трилинейное
6
1270=Сбросить настройки
7
1271=Яркость
8
1272=Насыщенность
9
10
1281=Сфера
11
1282=Цилиндр
12
1283=Куб
13
+1284=Полусфера
14
1285=Отслеживать ориентацию
15
1286=Отслеживать ориентацию (poor)
16
1287=Ориентировать звук
17
1288=Закрепить панорамный режим 360°
18
+?1293=Equiangular cubemap
19
+1294=Киноэкран
20
1300=Аудио
21
1301=Без звука
22
1302=Задержка звука
23
24
1400=Выбрать устройство
25
1401=О модуле...
26
1402=FPS Control
27
+1404=Эксклюзивный полноэкранный режим
28
1420=Верт. синхронизация
29
1421=Отображать FPS
30
1422=Ограничить использование CPU
31
32
1359=Снизу
33
1360=Plain text
34
1361=Lite HTML
35
+1370=Применить стереоформат
36
1590=Мелко
37
1591=Нормально
38
1592=Крупно
39
40
1705=Только в оконном режиме
41
1710=Скрыть панель навигации
42
1711=Открывать последний файл при старте
43
+1712=Поменять ракурсы местами в JPS/PNS
44
2000=Выберите видеофайл
45
2001=Выберите видеофайл с ЛЕВЫМ ракурсом
46
2002=Выберите видеофайл с ПРАВЫМ ракурсом
47
48
2005=Удаление файла
49
2006=Вы действительно хотите\n<b>удалить файл</b> минуя корзину?
50
2007=Активные декодеры:
51
+2008=Выберите аудиофайл
52
+2009=Выберите файл субтитров
53
2010=Выберите путь для сохранения картинки
54
2011=Ничего не открыто!
55
2012=Изображение недоступно для сохранения!
56
57
6055=X наклон - наверх
58
6056=X наклон - вниз
59
6057=Включить/выключить панорамный режим
60
+6058=Скрыть интерфейс
61
sview-20_08.tar.gz/StMoviePlayer/lang/spanish
Added
2
1
+(directory)
2
sview-20_08.tar.gz/StMoviePlayer/lang/spanish/StMoviePlayer.lng
Added
266
1
2
+# Spanish translation file for StMoviePlayer
3
+--------
4
+1002=Cambiar izquierdo/derecho
5
+1003=Revertir cambio izquierdo/derecho
6
+1004=Formato estereoscópico:
7
+1015=Abrir otra película
8
+1020=Reproducir/Pausa
9
+1021=Mostrar/Ocultar lista de reproducción
10
+1022=Reproducir archivo anterior
11
+1023=Reproducir archivo siguiente
12
+1029=Cambiar entre\npantalla completa/ventana
13
+1100=Medios
14
+1101=Abrir película...
15
+1102=Guardar instantánea...
16
+1103=Formato estereoscópico
17
+1170=Información del archivo
18
+1104=Dispositivo de audio
19
+1105=Mezclar
20
+1106=Archivos recientes
21
+1107=Decodificación de vídeo en GPU
22
+1108=UI Web
23
+1109=Salir
24
+1110=Desde un archivo
25
+1111=Archivos izquierdo+derecho
26
+1130=Fuente
27
+1131=Mono
28
+1132=Vista cruzada
29
+1133=Par paralelo
30
+1134=Sobre/bajo (D/I)
31
+1135=Sobre/bajo (I/D)
32
+1136=Entrelazado
33
+1137=Anaglifo rojo/cian
34
+1138=Anaglifo verde/rojo+azul
35
+1139=Anaglifo amarillo/azul
36
+1140=Fotograma-secuencial
37
+1141=2x720p en 1080p en mosaico
38
+1142=2 canales
39
+1160=Borrar historial
40
+1180=Apagar
41
+1181=Iniciar una vez
42
+1182=Iniciar siempre
43
+1185=Mostrar errores
44
+1186=¡No se puede iniciar la UI Web en el puerto {0}!
45
+1200=Ver
46
+1201=Salida estéreo
47
+1202=Pantalla completa
48
+1203=Restablecer
49
+1204=Cambiar izquierdo/derecho
50
+1205=Relación de visualización
51
+1206=Filtro más suave
52
+1207=Ajustar imagen
53
+1208=Panorámica
54
+1210=Estéreo
55
+1211=Vista izquierda
56
+1212=Vista derecha
57
+1213=Par paralelo
58
+1214=Vista cruzada
59
+1250=Fuente
60
+1251=Conservar al reiniciar
61
+1252=Corregir anamórfico 1080p/720p
62
+1260=Más cercano
63
+1261=Lineal
64
+1262=Mezclar entrelazado
65
+?1263=Trilineal
66
+1270=Restablecer predeterminados
67
+1271=Brillo
68
+1272=Saturación
69
+1273=Gamma
70
+1280=Plano
71
+1281=Esfera
72
+1282=Cilindro
73
+1283=Cubemap
74
+1284=Hemisferio
75
+1285=Orientación de pista
76
+1286=Orientación de pista (deficiente)
77
+1287=Orientar audio
78
+1288=Mantener en panorámica de 360°
79
+?1293=Equiangular cubemap
80
+1294=Teatro
81
+1300=Audio
82
+1301=Ninguna
83
+1302=Retraso de audio/vídeo
84
+1303=Adjuntar de archivo
85
+1320=Sincronización de audio/vídeo
86
+1321=Introduce un valor positivo si el audio está adelantado al vídeo, y negativo para lo contrario.
87
+1322=Retraso de audio:
88
+1323=segundo(s)
89
+1350=Subtítulos
90
+1351=Ninguno
91
+1353=Adjuntar de archivo
92
+1354=Tamaño de fuente
93
+1355=Paralaje
94
+1356=Interpretador de texto
95
+1357=Posición
96
+1358=Superior
97
+1359=Inferior
98
+1360=Texto sin formato
99
+1361=Lite HTML
100
+1370=Aplicar formato estéreo
101
+1400=Cambiar dispositivo
102
+1401=Acerca del complemento...
103
+1402=Control de FPS
104
+1404=Modo de pantalla completa exclusiva
105
+1420=Sincronización vertical
106
+1421=Mostrar medidor
107
+1422=Reducir uso de CPU
108
+1500=Ayuda
109
+1501=Acerca de...
110
+1502=Buscar actualizaciones
111
+1503=Texto de la licencia
112
+1504=Idioma (Language)
113
+1505=Bloquear suspensión
114
+1506=Consejos para el usuario
115
+1507=Características experimentales
116
+1508=Acerca del sistema
117
+1509=Escala de la interfaz
118
+1510=Teclas de acceso rápido
119
+1511=Ajustes
120
+1520=Ahora
121
+1521=Cada día
122
+1522=Cada semana
123
+1523=Cada año
124
+1524=Nunca
125
+1550=Nunca
126
+1551=Siempre
127
+1552=Durante la reproducción
128
+1553=En pantalla completa
129
+1590=Pequeño
130
+1591=Normal
131
+1592=Grande
132
+1593=Forzar HiDPI 2X
133
+1701=Salir de sView con escape
134
+1702=No salir
135
+1703=Con un clic
136
+1704=Con doble clic
137
+1705=Con un clic en modo ventana
138
+1710=Ocultar la barra de navegación del sistema
139
+1711=Abrir el último archivo reproducido al iniciar
140
+1712=JPS/PNS ve intercambio orden
141
+2000=Elije el archivo de vídeo para abrir
142
+2001=Elige el archivo de vídeo IZQUIERDO para abrir
143
+2002=Elije derecho archivo de vídeo DERECHO para abrir
144
+2003=Información del archivo
145
+2004=La información del archivo no está disponible
146
+2005=Eliminación de archivo
147
+2006=¿Realmente deseas eliminar completamente este archivo?
148
+2007=Descodificadores activos:
149
+2008=Elije el archivo de audio para añadir
150
+2009=Elije el archivo de subtítulos para añadir
151
+2010=Elije la ubicación para guardar la instantánea
152
+2011=¡Nada para guardar!
153
+2012=¡Instantánea no disponible!
154
+2013=Asignar nueva tecla de acceso rápido para la acción\n<i>{0}</i>
155
+2014=En conflicto con: <i>{0}</i>
156
+3000=sView - Reproductor de películas
157
+3001=versión
158
+3002=El reproductor de películas te permite reproducir un vídeo estereoscópico.\n © {0} Kirill Gavrilov <{1}>\nSitio oficial: {2}\n\nEste programa se distribuye bajo licencia GPL 3.0
159
+3003=Hay disponible una nueva versión de sView en el sitio oficial: www.sview.ru.\nPor favor, actualiza el programa.
160
+3004=Información del sistema
161
+4000=Cerrar
162
+4001=Cancelar
163
+4005=Restablecer
164
+4006=Guardar
165
+4007=Eliminar
166
+4008=Predeterminado
167
+4009=Predeterminados
168
+4010=Asignar
169
+5000=[izquierdo]
170
+5001=[derecho]
171
+5002=Nombre de archivo(s)
172
+5003=Dimensiones del vídeo
173
+5004=Tiempo de carga
174
+5005=ms
175
+5006=Relación de pixeles
176
+5007=Formato de píxel
177
+5008=(no almacenado en los metadatos)
178
+5009=(no coincide con los metadatos)
179
+5010=Duración
180
+5011=(no almacenado en los metadatos,\npero detectado en el nombre de archivo)
181
+5300=Título
182
+5301=Compositor
183
+5302=Artista
184
+5303=Artista del álbum
185
+5304=Álbum
186
+5305=Disco
187
+5306=Núm. de discos
188
+5307=Género
189
+5308=Comentario
190
+5309=Notas
191
+5310=Descripción
192
+5311=Editor
193
+5312=Derechos de autor
194
+5313=Codificador
195
+5314=Ingeniero
196
+5315=Fuente
197
+5316=Fecha de creación
198
+5317=Fecha
199
+5318=Año
200
+5319=Idioma
201
+5320=Pista
202
+5321=Núm. de pistas
203
+5322=Ganancia de la pista
204
+5323=Pico de la pista
205
+5324=Ganancia del álbum
206
+5325=Pico del álbum
207
+6000=Salir del programa
208
+6001=Cambiar entre pantalla completa/ventana
209
+6002=Mostrar/ocultar medidor de FPS
210
+6003=Formato estéreo: Automático
211
+6004=Formato estéreo: Mono
212
+6005=Formato estéreo: Sobre/bajo
213
+6006=Formato estéreo: En paralelo
214
+6007=Mostrar información del archivo
215
+6008=Lista de reproducción: Ir al primer elemento
216
+6009=Lista de reproducción: Ir al último elemento
217
+6010=Lista de reproducción: Ir al anterior elemento
218
+6011=Lista de reproducción: Ir al siguiente elemento
219
+6012=Lista de reproducción: Ir al anterior elemento [2]
220
+6013=Lista de reproducción: Ir al siguiente elemento [2]
221
+6014=Reproducir/pausar
222
+6015=Detener reproducción
223
+6016=Atrás 5 segundos
224
+6017=Adelante 5 segundos
225
+6018=Mostrar cuadro de diálogo para abrir archivo
226
+6019=Guardar instantánea
227
+6020=Eliminar el archivo del sistema de archivos
228
+6021=Silenciar/reactivar audio
229
+6022=Bajar volumen del audio
230
+6023=Subir volumen del audio
231
+6024=Anterior pista de audio
232
+6025=Siguiente pista de audio
233
+6026=Anterior pista de subtítulos
234
+6027=Siguiente pista de subtítulos
235
+6028=Copiar el texto de los subtítulos mostrados
236
+6029=Abrir URL del portapapeles
237
+6030=Mostrar/Ocultar lista de reproducción
238
+6031=Restablecer el ajuste de la imagen
239
+6032=Restablecer la posición de la imagen
240
+6033=Cambiar izquierdo/derecho
241
+6034=Corrección gamma: disminuir
242
+6035=Corrección gamma: aumentar
243
+6036=Separación DX: disminuir
244
+6037=Separación DX: aumentar
245
+6038=Separación DY: disminuir
246
+6039=Separación DY: aumentar
247
+6040=Separación angular: disminuir
248
+6041=Separación angular: aumentar
249
+6042=Rotar 90° a la izquierda
250
+6043=Rotar 90° a la derecha
251
+6044=Rotar a la izquierda
252
+6045=Rotar a la derecha
253
+6046=Activar/Desactivar modo panorámico
254
+6047=Barrido: navegar hacia la izquierda
255
+6048=Barrido: navegar hacia la derecha
256
+6049=Barrido: navegar hacia arriba
257
+6050=Barrido: navegar hacia abajo
258
+6051=Escala: aumentar
259
+6052=Escala: reducir
260
+6053=Rotación Y: izquierda
261
+6054=Rotación Y: derecha
262
+6055=Rotación X: arriba
263
+6056=Rotación X: abajo
264
+6057=Activar/Desactivar modo panorámico
265
+6058=Mostrar/ocultar GUI
266
sview-17_04.tar.gz/StOutAnaglyph/StOutAnaglyph.cpp -> sview-20_08.tar.gz/StOutAnaglyph/StOutAnaglyph.cpp
Changed
10
1
2
StString& aDescr = aLangMap.changeValueId(STTR_PLUGIN_DESCRIPTION,
3
"(C) {0} Kirill Gavrilov <{1}>\nOfficial site: {2}\n\nThis library is distributed under LGPL3.0");
4
myAbout = aTitle + '\n' + aVerString + " " + StVersionInfo::getSDKVersionString() + "\n \n"
5
- + aDescr.format("2007-2017", "kirill@sview.ru", "www.sview.ru");
6
+ + aDescr.format("2007-2020", "kirill@sview.ru", "www.sview.ru");
7
}
8
9
StOutAnaglyph::StOutAnaglyph(const StHandle<StResourceManager>& theResMgr,
10
sview-17_04.tar.gz/StOutAnaglyph/StOutAnaglyph.rc -> sview-20_08.tar.gz/StOutAnaglyph/StOutAnaglyph.rc
Changed
10
1
2
BEGIN
3
VALUE "FileDescription", "Anaglyph Renderer library\000"
4
VALUE "FileVersion", SVIEW_SDK_VER_STRING "\000"
5
- VALUE "LegalCopyright", "\251 2007-2017 Kirill Gavrilov\000"
6
+ VALUE "LegalCopyright", "\251 2007-2020 Kirill Gavrilov and sView developers\000"
7
VALUE "ProductName", "StOutAnaglyph\000"
8
VALUE "ProductVersion", SVIEW_SDK_VER_STRING "\000"
9
VALUE "OfficialSite", "www.sview.ru\000"
10
sview-20_08.tar.gz/StOutAnaglyph/lang/spanish
Added
2
1
+(directory)
2
sview-20_08.tar.gz/StOutAnaglyph/lang/spanish/StOutAnaglyph.lng
Added
21
1
2
+# Spanish translation file for StOutAnalygph
3
+--------
4
+1000=Gafas anaglíficas
5
+1001=Gafas simples con filtros de color. Usadas comúnmente
6
+1010=Tipo de gafas
7
+1011=Rojo-cian (R+GB)
8
+1012=Amarillo-azul (RG+B)
9
+1013=Verde-magenta (G+RB)
10
+1102=Filtro rojo-cian
11
+1120=Simple
12
+1121=Optimizado
13
+1122=En gris
14
+1123=Oscuro
15
+1103=Filtro amarillo-azul
16
+1130=Simple
17
+1131=Dubios
18
+2000=sView - Módulo de salida anaglífica
19
+2001=versión
20
+2002=© {0} Kirill Gavrilov <{1}>\nSitio oficial: {2}
21
sview-17_04.tar.gz/StOutDistorted/StOutDistorted.cpp -> sview-20_08.tar.gz/StOutDistorted/StOutDistorted.cpp
Changed
566
1
2
/**
3
* StOutDistorted, class providing stereoscopic output in anamorph side by side format using StCore toolkit.
4
- * Copyright © 2013-2017 Kirill Gavrilov <kirill@sview.ru>
5
+ * Copyright © 2013-2020 Kirill Gavrilov <kirill@sview.ru>
6
*
7
* Distributed under the Boost Software License, Version 1.0.
8
* See accompanying file license-boost.txt or copy at
9
10
#include <StGL/StGLArbFbo.h>
11
#include <StGLCore/StGLCore20.h>
12
#include <StGLMesh/StGLTextureQuad.h>
13
+#include <StGLStereo/StGLProjCamera.h>
14
#include <StSettings/StSettings.h>
15
#include <StSettings/StTranslations.h>
16
#include <StSettings/StEnumParam.h>
17
18
#ifdef _MSC_VER
19
#pragma comment(lib, "openvr_api.lib")
20
#endif
21
-#elif defined(ST_HAVE_LIBOVR)
22
- #include <OVR.h>
23
- #include <OVR_CAPI_GL.h>
24
-
25
- #ifdef _MSC_VER
26
- #pragma comment(lib, "LibOVR.lib")
27
- #endif
28
#endif
29
30
namespace {
31
32
void StOutDistorted::updateAbout() {
33
myAbout = myAboutTitle + '\n' + myAboutVerString + " " + StVersionInfo::getSDKVersionString() + "\n \n"
34
+ (!myAboutVrDevice.isEmpty() ? ("Connected hardware: " + myAboutVrDevice + "\n \n") : "")
35
- + myAboutDescr.format("2013-2017", "kirill@sview.ru", "www.sview.ru");
36
+ + myAboutDescr.format("2013-2020", "kirill@sview.ru", "www.sview.ru");
37
#ifdef ST_HAVE_OPENVR
38
myAbout = myAbout + "\n \n"
39
+ "This software uses OpenVR library:\n"
40
41
myVrMarginsBottom(0.35),
42
myVrMarginsLeft(0.33),
43
myVrMarginsRight(0.33),
44
- myVrRendSizeX(0),
45
- myVrRendSizeY(0),
46
+ myVrFrequency(0),
47
+ myVrAspectRatio(1.0f),
48
+ myVrFieldOfView(-1.0f),
49
+ myVrIOD(0.0f),
50
myVrTrackOrient(false),
51
myVrToDrawMsg(false),
52
#ifdef ST_HAVE_OPENVR
53
myVrHmd(NULL),
54
myVrTrackedPoses(new vr::TrackedDevicePose_t[vr::k_unMaxTrackedDeviceCount]),
55
-#elif defined(ST_HAVE_LIBOVR)
56
- myVrHmd(NULL),
57
- myOvrSwapTexture(NULL),
58
- myOvrMirrorTexture(NULL),
59
- myOvrMirrorFbo(0),
60
#endif
61
myToShowCursor(true),
62
myToCompressMem(myInstancesNb.increment() > 1),
63
64
myCanHdmiPack(false),
65
myIsHdmiPack(false),
66
myIsForcedFboUsage(false) {
67
-#ifdef ST_HAVE_LIBOVR
68
- myOvrSwapFbo[0] = 0;
69
- myOvrSwapFbo[1] = 0;
70
-#endif
71
const StSearchMonitors& aMonitors = StWindow::getMonitors();
72
73
// detect connected displays
74
75
if(vr::VR_IsHmdPresent()) {
76
aSupportOpenVr = ST_DEVICE_SUPPORT_PREFER;
77
}
78
-#elif defined(ST_HAVE_LIBOVR)
79
- const ovrResult anOvrRes = ovr_Initialize(NULL);
80
- if(!OVR_SUCCESS(anOvrRes)) {
81
- ST_ERROR_LOG("StOutDistorted, OVR initialization has failed!");
82
- } else {
83
- aSupportOpenVr = ST_DEVICE_SUPPORT_HIGHT;
84
- }
85
#endif
86
87
// devices list
88
89
vr::VR_Shutdown();
90
myVrHmd = NULL;
91
}
92
- #elif defined(ST_HAVE_LIBOVR)
93
- if(myOvrSwapFbo[0] != 0) {
94
- myContext->arbFbo->glDeleteFramebuffers(2, myOvrSwapFbo);
95
- myOvrSwapFbo[0] = 0;
96
- myOvrSwapFbo[1] = 0;
97
- }
98
- if(myOvrSwapTexture != NULL) {
99
- ovr_DestroySwapTextureSet(myVrHmd, myOvrSwapTexture);
100
- myOvrSwapTexture = NULL;
101
- }
102
- if(myOvrMirrorFbo != 0) {
103
- myContext->arbFbo->glDeleteFramebuffers(1, &myOvrMirrorFbo);
104
- myOvrMirrorFbo = NULL;
105
- }
106
- if(myOvrMirrorTexture != NULL) {
107
- ovr_DestroyMirrorTexture(myVrHmd, &myOvrMirrorTexture->Texture);
108
- myOvrMirrorTexture = NULL;
109
- }
110
- if(myVrHmd != NULL) {
111
- ovr_Destroy(myVrHmd);
112
- myVrHmd = NULL;
113
- }
114
#endif
115
116
myProgramFlat->release(*myContext);
117
118
119
#ifdef ST_HAVE_OPENVR
120
delete[] myVrTrackedPoses;
121
-#elif defined(ST_HAVE_LIBOVR)
122
- ovr_Shutdown();
123
#endif
124
}
125
126
127
myContext = StWindow::getContext();
128
myContext->setMessagesQueue(myMsgQueue);
129
myIsBroken = false;
130
+ myVrFrequency = 0;
131
+ myVrFieldOfView = -1.0f;
132
if(!myContext->isGlGreaterEqual(2, 0)) {
133
myMsgQueue->pushError(stCString("OpenGL 2.0 is required by Distorted Output"));
134
myIsBroken = true;
135
136
const StString aVrManuf = getVrTrackedDeviceString(myVrHmd, vr::k_unTrackedDeviceIndex_Hmd, vr::Prop_ManufacturerName_String);
137
const StString aVrDriver = getVrTrackedDeviceString(myVrHmd, vr::k_unTrackedDeviceIndex_Hmd, vr::Prop_TrackingSystemName_String);
138
const StString aVrDisplay = getVrTrackedDeviceString(myVrHmd, vr::k_unTrackedDeviceIndex_Hmd, vr::Prop_SerialNumber_String);
139
+ myVrFrequency = myVrHmd->GetFloatTrackedDeviceProperty(vr::k_unTrackedDeviceIndex_Hmd, vr::Prop_DisplayFrequency_Float);
140
+ updateVRProjectionFrustums();
141
142
- uint32_t aRenderSizeX = 0;
143
- uint32_t aRenderSizeY = 0;
144
+ uint32_t aRenderSizeX = 0, aRenderSizeY = 0;
145
myVrHmd->GetRecommendedRenderTargetSize(&aRenderSizeX, &aRenderSizeY);
146
myAboutVrDevice = aVrManuf + " " + aVrDriver + "\n"
147
- + aVrDisplay + " [" + aRenderSizeX + "x" + aRenderSizeY + "]";
148
- myVrRendSizeX = int(aRenderSizeX);
149
- myVrRendSizeY = int(aRenderSizeY);
150
+ + aVrDisplay + " [" + aRenderSizeX + "x" + aRenderSizeY + "@" + myVrFrequency + "]";
151
+ myVrRendSize.x() = int(aRenderSizeX);
152
+ myVrRendSize.y() = int(aRenderSizeY);
153
updateAbout();
154
}
155
-
156
-#elif defined(ST_HAVE_LIBOVR)
157
- if(myDevice == DEVICE_HMD) {
158
- ovrGraphicsLuid aLuid;
159
- const ovrResult anOvrRes = ovr_Create(&myVrHmd, &aLuid);
160
- if(myVrHmd == NULL
161
- || !OVR_SUCCESS(anOvrRes)) {
162
- myMsgQueue->pushError(stCString("StOutDistorted, Oculus Rift is not connected!"));
163
- myVrHmd = NULL;
164
- return true;
165
- }
166
- }
167
-
168
- if(myVrHmd != NULL) {
169
- ovrHmdDesc anHmdDesc = ovr_GetHmdDesc(myVrHmd);
170
- ovrSizei aWinSize = { anHmdDesc.Resolution.w / 2, anHmdDesc.Resolution.h / 2 };
171
-
172
- ST_DEBUG_LOG("libOVR Resolution: " + anHmdDesc.Resolution.w + "x" + anHmdDesc.Resolution.h);
173
- if(isMovable()) {
174
- StRect<int32_t> aRect = StWindow::getPlacement();
175
- aRect.right() = aRect.left() + aWinSize.w;
176
- aRect.bottom() = aRect.top() + aWinSize.h;
177
- StWindow::setPlacement(aRect, false);
178
- }
179
-
180
- ovrResult anOvrRes = ovr_CreateMirrorTextureGL(myVrHmd, GL_SRGB8_ALPHA8, aWinSize.w, aWinSize.h, (ovrTexture** )&myOvrMirrorTexture);
181
- if(!OVR_SUCCESS(anOvrRes)) {
182
- myMsgQueue->pushError(stCString("StOutDistorted, Failed to create mirror texture!"));
183
- myIsBroken = true;
184
- return true;
185
- }
186
-
187
- const GLuint anFboReadBack = myContext->stglFramebufferRead();
188
- myContext->arbFbo->glGenFramebuffers(1, &myOvrMirrorFbo);
189
- myContext->stglBindFramebufferRead(myOvrMirrorFbo);
190
- myContext->arbFbo->glFramebufferTexture2D(GL_READ_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, myOvrMirrorTexture->OGL.TexId, 0);
191
- myContext->stglBindFramebufferRead(anFboReadBack);
192
-
193
- ovrSizei anEyeSizes[2] = {
194
- ovr_GetFovTextureSize(myVrHmd, ovrEye_Left, anHmdDesc.DefaultEyeFov[ovrEye_Left], 1),
195
- ovr_GetFovTextureSize(myVrHmd, ovrEye_Right, anHmdDesc.DefaultEyeFov[ovrEye_Right], 1)
196
- };
197
- myVrRendSizeX = stMax(anEyeSizes[0].w, anEyeSizes[1].w);
198
- myVrRendSizeY = stMax(anEyeSizes[0].h, anEyeSizes[1].h);
199
- anOvrRes = ovr_CreateSwapTextureSetGL(myVrHmd, GL_SRGB8_ALPHA8, myVrRendSizeX * 2, myVrRendSizeY, &myOvrSwapTexture);
200
- if(!OVR_SUCCESS(anOvrRes)
201
- || myOvrSwapTexture->TextureCount < 2) {
202
- myMsgQueue->pushError(stCString("StOutDistorted, Failed to create swap texture!"));
203
- myIsBroken = true;
204
- return true;
205
- }
206
-
207
- myOvrSwapTexture->CurrentIndex = 0;
208
- myContext->arbFbo->glGenFramebuffers(2, myOvrSwapFbo);
209
- myContext->stglBindFramebufferRead(myOvrSwapFbo[0]);
210
- myContext->arbFbo->glFramebufferTexture2D(GL_READ_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D,
211
- ((ovrGLTexture* )&myOvrSwapTexture->Textures[0])->OGL.TexId, 0);
212
- myContext->stglBindFramebufferRead(myOvrSwapFbo[1]);
213
- myContext->arbFbo->glFramebufferTexture2D(GL_READ_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D,
214
- ((ovrGLTexture* )&myOvrSwapTexture->Textures[1])->OGL.TexId, 0);
215
- myContext->stglBindFramebufferRead(anFboReadBack);
216
- }
217
#endif
218
219
if(myDevice == DEVICE_HMD) {
220
221
return true;
222
}
223
224
+void StOutDistorted::updateVRProjectionFrustums() {
225
+#ifdef ST_HAVE_OPENVR
226
+ StRect<float> aFrustL, aFrustR;
227
+ myVrHmd->GetProjectionRaw(vr::Eye_Left, &aFrustL.left(), &aFrustL.right(), &aFrustL.top(), &aFrustL.bottom());
228
+ myVrHmd->GetProjectionRaw(vr::Eye_Right, &aFrustR.left(), &aFrustR.right(), &aFrustR.top(), &aFrustR.bottom());
229
+ myVrFrustumL = aFrustL;
230
+ myVrFrustumR = aFrustR;
231
+ std::swap(myVrFrustumL.top(), myVrFrustumL.bottom());
232
+ std::swap(myVrFrustumR.top(), myVrFrustumR.bottom());
233
+
234
+ const StVec2<double> aTanHalfFov(StVec4<float>(-aFrustL.left(), aFrustL.right(), -aFrustR.left(), aFrustR.right()).maxComp(),
235
+ StVec4<float>(-aFrustL.top(), aFrustL.bottom(), -aFrustR.top(), aFrustR.bottom()).maxComp());
236
+ myVrAspectRatio = float(aTanHalfFov.x() / aTanHalfFov.y());
237
+ myVrFieldOfView = float(2.0 * std::atan(aTanHalfFov.y()) * 180.0 / M_PI);
238
+
239
+ // Intra-ocular Distance can be changed in runtime
240
+ //const vr::HmdMatrix34_t aLeftToHead = myContext->System->GetEyeToHeadTransform (vr::Eye_Left);
241
+ //const vr::HmdMatrix34_t aRightToHead = myContext->System->GetEyeToHeadTransform (vr::Eye_Right);
242
+ //myVrIOD = aRightToHead.m[0][3] - aLeftToHead.m[0][3];
243
+ myVrIOD = myVrHmd->GetFloatTrackedDeviceProperty(vr::k_unTrackedDeviceIndex_Hmd, vr::Prop_UserIpdMeters_Float);
244
+#else
245
+ (void )myVrIOD;
246
+#endif
247
+}
248
+
249
+float StOutDistorted::getMaximumTargetFps() const {
250
+ return myVrFrequency > 24
251
+ ? myVrFrequency
252
+ : StWindow::getMaximumTargetFps();
253
+}
254
+
255
void StOutDistorted::processEvents() {
256
StWindow::processEvents();
257
258
259
return;
260
}
261
262
- const float aLensDisp = getLensDist() * 0.5f;
263
- double aGlLeft = -1.0;
264
- double aGlTop = 1.0;
265
- double aGlSizeX = 2.0;
266
- double aGlSizeY = 2.0;
267
+ double aGlLeft = -1.0, aGlTop = 1.0;
268
+ double aGlSizeX = 2.0, aGlSizeY = 2.0;
269
+ float aLensDisp = theView == ST_DRAW_LEFT ? getLensDist() : -getLensDist();
270
if(isHmdOutput()) {
271
aGlLeft = -1.0 + myVrMarginsLeft * 2.0;
272
aGlTop = 1.0 - myVrMarginsTop * 2.0;
273
aGlSizeX = 2.0 - (myVrMarginsLeft + myVrMarginsRight) * 2.0;
274
aGlSizeY = 2.0 - (myVrMarginsTop + myVrMarginsBottom) * 2.0;
275
+
276
+ StGLProjCamera aProjCam;
277
+ aProjCam.setPerspective(true);
278
+ //aProjCam.setFOVy(myVrFieldOfView);
279
+ aProjCam.resize(myVrAspectRatio);
280
+ aProjCam.setCustomProjection(myVrFrustumL, myVrFrustumR);
281
+ aProjCam.setView(theView);
282
+
283
+ const StGLVec4 aTestProj = aProjCam.getProjMatrix() * StGLVec4(0, 0, aProjCam.getZScreen(), 1.0f);
284
+ aLensDisp = aTestProj.x() / aTestProj.w();
285
}
286
287
// compute cursor position
288
- StArray<StGLVec4> aVerts(4);
289
const float aCurLeft = float(aGlLeft + theCursorPos.x() * aGlSizeX);
290
const float aCurTop = float(aGlTop - theCursorPos.y() * aGlSizeY);
291
if(isHmdOutput()) {
292
293
break;
294
}
295
}
296
- if(theView == ST_DRAW_LEFT) {
297
- aVerts[0] = StGLVec4( 2.0f * aLensDisp + aCurLeft + aCurWidth, aCurTop - aCurHeight, 0.0f, 1.0f);
298
- aVerts[1] = StGLVec4( 2.0f * aLensDisp + aCurLeft + aCurWidth, aCurTop, 0.0f, 1.0f);
299
- aVerts[2] = StGLVec4( 2.0f * aLensDisp + aCurLeft, aCurTop - aCurHeight, 0.0f, 1.0f);
300
- aVerts[3] = StGLVec4( 2.0f * aLensDisp + aCurLeft, aCurTop, 0.0f, 1.0f);
301
- } else {
302
- aVerts[0] = StGLVec4(-2.0f * aLensDisp + aCurLeft + aCurWidth, aCurTop - aCurHeight, 0.0f, 1.0f);
303
- aVerts[1] = StGLVec4(-2.0f * aLensDisp + aCurLeft + aCurWidth, aCurTop, 0.0f, 1.0f);
304
- aVerts[2] = StGLVec4(-2.0f * aLensDisp + aCurLeft, aCurTop - aCurHeight, 0.0f, 1.0f);
305
- aVerts[3] = StGLVec4(-2.0f * aLensDisp + aCurLeft, aCurTop, 0.0f, 1.0f);
306
- }
307
+
308
+ StArray<StGLVec4> aVerts(4);
309
+ aVerts[0] = StGLVec4(aLensDisp + aCurLeft + aCurWidth, aCurTop - aCurHeight, 0.0f, 1.0f);
310
+ aVerts[1] = StGLVec4(aLensDisp + aCurLeft + aCurWidth, aCurTop, 0.0f, 1.0f);
311
+ aVerts[2] = StGLVec4(aLensDisp + aCurLeft, aCurTop - aCurHeight, 0.0f, 1.0f);
312
+ aVerts[3] = StGLVec4(aLensDisp + aCurLeft, aCurTop, 0.0f, 1.0f);
313
myCurVertsBuf.init(*myContext, aVerts);
314
315
myContext->core20fwd->glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
316
317
}
318
319
bool StOutDistorted::hasOrientationSensor() const {
320
-#if defined(ST_HAVE_OPENVR) || defined(ST_HAVE_LIBOVR)
321
+#if defined(ST_HAVE_OPENVR)
322
if(myVrHmd != NULL) {
323
return true;
324
}
325
326
}
327
328
bool StOutDistorted::toTrackOrientation() const {
329
-#if defined(ST_HAVE_OPENVR) || defined(ST_HAVE_LIBOVR)
330
+#if defined(ST_HAVE_OPENVR)
331
if(myVrHmd != NULL) {
332
return myVrTrackOrient;
333
}
334
335
}
336
337
void StOutDistorted::setTrackOrientation(const bool theToTrack) {
338
-#if defined(ST_HAVE_OPENVR) || defined(ST_HAVE_LIBOVR)
339
+#if defined(ST_HAVE_OPENVR)
340
if(myVrHmd != NULL) {
341
myVrTrackOrient = theToTrack;
342
return;
343
344
StQuaternion<double> StOutDistorted::getDeviceOrientation() const {
345
if(myVrTrackOrient
346
&& !myIsBroken) {
347
- #if defined(ST_HAVE_OPENVR) || defined(ST_HAVE_LIBOVR)
348
+ #if defined(ST_HAVE_OPENVR)
349
if(myVrHmd != NULL) {
350
return myVrOrient;
351
}
352
353
return StWindow::getDeviceOrientation();
354
}
355
356
+bool StOutDistorted::getCustomProjection(StRectF_t& theLeft, StRectF_t& theRight) const {
357
+ if(!isHmdOutput()) {
358
+ return false;
359
+ }
360
+
361
+ theLeft = myVrFrustumL;
362
+ theRight = myVrFrustumR;
363
+ return true;
364
+}
365
+
366
+StGLBoxPx StOutDistorted::stglViewport(const int theWinEnum) const {
367
+ if(!isHmdOutput()) {
368
+ return StWindow::stglViewport(theWinEnum);
369
+ }
370
+
371
+ StGLBoxPx aBox;
372
+ aBox.x() = aBox.y() = 0;
373
+ aBox.width() = myVrRendSize.x();
374
+ aBox.height() = myVrRendSize.y();
375
+ return aBox;
376
+}
377
+
378
StMarginsI StOutDistorted::getMargins() const {
379
if(isHmdOutput()) {
380
- const StGLBoxPx aViewPort = StWindow::stglViewport(ST_WIN_MASTER);
381
- const int aSizeX = aViewPort.width();
382
- const int aSizeY = aViewPort.height();
383
StMarginsI aMargins;
384
- aMargins.left = int(double(aSizeX) * myVrMarginsLeft);
385
- aMargins.right = int(double(aSizeX) * myVrMarginsRight);
386
- aMargins.top = int(double(aSizeY) * myVrMarginsTop);
387
- aMargins.bottom = int(double(aSizeY) * myVrMarginsBottom);
388
+ aMargins.left = int(double(myVrRendSize.x()) * myVrMarginsLeft);
389
+ aMargins.right = int(double(myVrRendSize.x()) * myVrMarginsRight);
390
+ aMargins.top = int(double(myVrRendSize.y()) * myVrMarginsTop);
391
+ aMargins.bottom = int(double(myVrRendSize.y()) * myVrMarginsBottom);
392
return aMargins;
393
}
394
return StMarginsI();
395
396
return StWindow::getScaleFactor();
397
}
398
399
- // within direct rendering mode HMD is not visible to the system and thus is not registered as StMonitor,
400
- // therefore we need to override scale factor here to avoid incorrect scaling
401
- return 0.8f;
402
+ // TODO this is calibrated for HTC Vive; applying to HMDs with another FOV might give bad results
403
+ return float(myVrRendSize.x()) / 1280.0f;
404
}
405
406
void StOutDistorted::checkHdmiPack() {
407
408
return;
409
}
410
411
- if(!myFrBuffer->initLazy(*myContext, GL_RGBA8, myVrRendSizeX, myVrRendSizeY, StWindow::hasDepthBuffer())) {
412
- myIsBroken = true;
413
- myMsgQueue->pushError(stCString("OpenVR output - critical error:\nFrame Buffer Object resize failed!"));
414
- vr::VR_Shutdown();
415
- myVrHmd = NULL;
416
- return;
417
+ // force resizing instead of lazy resize as we do not pass texture bounds
418
+ const vr::VRTextureBounds_t* aTexBounds = NULL;
419
+ if(!myFrBuffer->isValid()
420
+ || myFrBuffer->getSizeX() != myVrRendSize.x()
421
+ || myFrBuffer->getSizeY() != myVrRendSize.y()) {
422
+ if(!myFrBuffer->init(*myContext, GL_RGBA8, myVrRendSize.x(), myVrRendSize.y(), StWindow::hasDepthBuffer())) {
423
+ myIsBroken = true;
424
+ myMsgQueue->pushError(stCString("OpenVR output - critical error:\nFrame Buffer Object resize failed!"));
425
+ vr::VR_Shutdown();
426
+ myVrHmd = NULL;
427
+ return;
428
+ }
429
}
430
431
// draw into virtual frame buffers (textures)
432
433
stglDrawCursor(aCursorPos, ST_DRAW_LEFT);
434
435
vr::Texture_t aVRTexture = { (void* )(size_t )myFrBuffer->getTextureColor()->getTextureId(), vr::TextureType_OpenGL, vr::ColorSpace_Gamma };
436
- const vr::EVRCompositorError aVRError = vr::VRCompositor()->Submit(vr::Eye_Left, &aVRTexture);
437
+ const vr::EVRCompositorError aVRError = vr::VRCompositor()->Submit(vr::Eye_Left, &aVRTexture, aTexBounds);
438
if(aVRError != vr::VRCompositorError_None) {
439
//myMsgQueue->pushError(getVRCompositorError(aVRError));
440
ST_ERROR_LOG(getVRCompositorError(aVRError));
441
442
aRotMat[aCol][aRow] = aHeadPos.m[aCol][aRow];
443
}
444
}
445
+
446
myVrOrient.setMatrix(aRotMat);
447
- }
448
+ updateVRProjectionFrustums();
449
+ }
450
}
451
452
// real screen buffer
453
454
myVrMsgTimer.stop();
455
}
456
}
457
-#elif defined(ST_HAVE_LIBOVR)
458
- const StGLBoxPx aVPBoth = StWindow::stglViewport(ST_WIN_ALL);
459
- const StPointD_t aCursorPos = getMousePos();
460
- if(myVrHmd == NULL
461
- || myIsBroken) {
462
- return;
463
- }
464
-
465
- ovrHmdDesc anHmdDesc = ovr_GetHmdDesc(myVrHmd);
466
- ovrEyeRenderDesc anEyeRenderDesc[2] = {
467
- ovr_GetRenderDesc(myVrHmd, ovrEye_Left, anHmdDesc.DefaultEyeFov[0]),
468
- ovr_GetRenderDesc(myVrHmd, ovrEye_Right, anHmdDesc.DefaultEyeFov[1])
469
- };
470
- ovrViewScaleDesc aViewScaleDesc;
471
- aViewScaleDesc.HmdSpaceToWorldScaleInMeters = 1.0f;
472
- aViewScaleDesc.HmdToEyeViewOffset[0] = anEyeRenderDesc[0].HmdToEyeViewOffset;
473
- aViewScaleDesc.HmdToEyeViewOffset[1] = anEyeRenderDesc[1].HmdToEyeViewOffset;
474
-
475
- const StGLBoxPx aViewPortL = {{ 0, 0,
476
- myVrRendSizeX, myVrRendSizeY }};
477
- const StGLBoxPx aViewPortR = {{ myVrRendSizeX, 0,
478
- myVrRendSizeX, myVrRendSizeY }};
479
-
480
- ovrLayerEyeFov aLayerFov;
481
- aLayerFov.Header.Type = ovrLayerType_EyeFov;
482
- aLayerFov.Header.Flags = ovrLayerFlag_TextureOriginAtBottomLeft;
483
- aLayerFov.ColorTexture[0] = myOvrSwapTexture;
484
- aLayerFov.ColorTexture[1] = NULL;
485
- aLayerFov.Viewport[0].Pos.x = aViewPortL.x();
486
- aLayerFov.Viewport[0].Pos.y = aViewPortL.y();
487
- aLayerFov.Viewport[0].Size.w= aViewPortL.width();
488
- aLayerFov.Viewport[0].Size.h= aViewPortL.height();
489
- aLayerFov.Viewport[1].Pos.x = aViewPortR.x();
490
- aLayerFov.Viewport[1].Pos.y = aViewPortR.y();
491
- aLayerFov.Viewport[1].Size.w= aViewPortR.width();
492
- aLayerFov.Viewport[1].Size.h= aViewPortR.height();
493
- aLayerFov.Fov[0] = anHmdDesc.DefaultEyeFov[0];
494
- aLayerFov.Fov[1] = anHmdDesc.DefaultEyeFov[1];
495
- aLayerFov.SensorSampleTime = ovr_GetTimeInSeconds();
496
- const double aPredictedTime = ovr_GetPredictedDisplayTime(myVrHmd, 0);
497
- ovrTrackingState anHmdState = ovr_GetTrackingState(myVrHmd, aPredictedTime, ovrTrue);
498
- ovr_CalcEyePoses(anHmdState.HeadPose.ThePose, aViewScaleDesc.HmdToEyeViewOffset, aLayerFov.RenderPose);
499
- myVrOrient = StQuaternion<double>((double )aLayerFov.RenderPose[0].Orientation.x,
500
- (double )aLayerFov.RenderPose[0].Orientation.y,
501
- (double )aLayerFov.RenderPose[0].Orientation.z,
502
- (double )aLayerFov.RenderPose[0].Orientation.w);
503
-
504
- // draw Left View into virtual frame buffer
505
- myContext->stglResizeViewport(aViewPortL);
506
- myContext->stglSetScissorRect(aViewPortL, false);
507
- myContext->stglBindFramebuffer(myOvrSwapFbo[myOvrSwapTexture->CurrentIndex]);
508
- StWindow::signals.onRedraw(ST_DRAW_LEFT);
509
- stglDrawCursor(aCursorPos, ST_DRAW_LEFT);
510
-
511
- // draw Right View into virtual frame buffer
512
- myContext->stglResizeViewport(aViewPortR);
513
- myContext->stglSetScissorRect(aViewPortR, false);
514
- StWindow::signals.onRedraw(ST_DRAW_RIGHT);
515
- stglDrawCursor(aCursorPos, ST_DRAW_RIGHT);
516
- myContext->stglBindFramebuffer(StGLFrameBuffer::NO_FRAMEBUFFER);
517
-
518
- ovrLayerHeader* aLayers = &aLayerFov.Header;
519
- ovrResult anOvrRes = ovr_SubmitFrame(myVrHmd, 0, &aViewScaleDesc, &aLayers, 1);
520
- myOvrSwapTexture->CurrentIndex = myOvrSwapTexture->CurrentIndex == 0 ? 1 : 0;
521
- if(!OVR_SUCCESS(anOvrRes)) {
522
- myMsgQueue->pushError(stCString("StOutDistorted, Failed to submit swap texture!"));
523
- myIsBroken = true;
524
- }
525
-
526
- myContext->stglResizeViewport(aVPBoth);
527
- myContext->stglResetScissorRect();
528
- myContext->core20fwd->glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
529
-
530
- myContext->stglBindFramebufferRead(myOvrMirrorFbo);
531
- myContext->stglBindFramebufferDraw(StGLFrameBuffer::NO_FRAMEBUFFER);
532
- GLint aSrcSizeX = myOvrMirrorTexture->OGL.Header.TextureSize.w;
533
- GLint aSrcSizeY = myOvrMirrorTexture->OGL.Header.TextureSize.h;
534
- myContext->arbFbo->glBlitFramebuffer(0, aSrcSizeY, aSrcSizeX, 0,
535
- 0, 0, aVPBoth.width(), aVPBoth.height(),
536
- GL_COLOR_BUFFER_BIT, GL_NEAREST);
537
- myContext->stglBindFramebufferRead(StGLFrameBuffer::NO_FRAMEBUFFER);
538
-
539
- myFPSControl.sleepToTarget(); // decrease FPS to target by thread sleeps
540
- StWindow::stglSwap(ST_WIN_ALL);
541
- ++myFPSControl;
542
#endif
543
}
544
545
546
547
double aForcedAspect = -1.0;
548
if(isHmdOutput()) {
549
- if(myVrRendSizeX != 0 && myVrRendSizeY != 0) {
550
- aForcedAspect = double(myVrRendSizeX) / double(myVrRendSizeY);
551
- }
552
+ //if(myVrRendSize.x() != 0 && myVrRendSize.y() != 0) { aForcedAspect = double(myVrRendSize.x()) / double(myVrRendSize.y()); }
553
+ aForcedAspect = myVrAspectRatio;
554
}
555
556
StWinSplit aWinSplit = StWinSlave_splitOff;
557
558
return;
559
}
560
561
-#if defined(ST_HAVE_OPENVR) || defined(ST_HAVE_LIBOVR)
562
+#if defined(ST_HAVE_OPENVR)
563
if(myVrHmd != NULL
564
&& !myIsBroken) {
565
stglDrawVR();
566
sview-17_04.tar.gz/StOutDistorted/StOutDistorted.h -> sview-20_08.tar.gz/StOutDistorted/StOutDistorted.h
Changed
102
1
2
/**
3
* StOutDistorted, class providing stereoscopic output in anamorph side by side format using StCore toolkit.
4
- * Copyright © 2013-2017 Kirill Gavrilov <kirill@sview.ru>
5
+ * Copyright © 2013-2020 Kirill Gavrilov <kirill@sview.ru>
6
*
7
* Distributed under the Boost Software License, Version 1.0.
8
* See accompanying file license-boost.txt or copy at
9
10
struct TrackedDevicePose_t;
11
}
12
13
-typedef struct ovrHmdStruct* ovrSession;
14
-typedef union ovrGLTexture_s ovrGLTexture;
15
-typedef struct ovrSwapTextureSet_ ovrSwapTextureSet;
16
-
17
/**
18
* This class implements stereoscopic rendering on displays
19
* which require software distortion correction.
20
21
ST_CPPEXPORT virtual void stglDraw() ST_ATTR_OVERRIDE;
22
23
/**
24
+ * Get viewport for specified subwindow.
25
+ */
26
+ ST_CPPEXPORT virtual StGLBoxPx stglViewport(const int theWinEnum) const ST_ATTR_OVERRIDE;
27
+
28
+ /**
29
* Show/Hide mouse cursor.
30
* @param theToShow true to show cursor
31
*/
32
- ST_CPPEXPORT virtual void showCursor(const bool theToShow);
33
+ ST_CPPEXPORT virtual void showCursor(const bool theToShow) ST_ATTR_OVERRIDE;
34
35
/**
36
* Return true if device has orientation sensor.
37
38
ST_CPPEXPORT virtual StQuaternion<double> getDeviceOrientation() const ST_ATTR_OVERRIDE;
39
40
/**
41
+ * Return custom stereo projection frustums.
42
+ */
43
+ ST_CPPEXPORT virtual bool getCustomProjection(StRectF_t& theLeft, StRectF_t& theRight) const ST_ATTR_OVERRIDE;
44
+
45
+ /**
46
* Return margins for working area.
47
*/
48
ST_CPPEXPORT virtual StMarginsI getMargins() const ST_ATTR_OVERRIDE;
49
50
*/
51
ST_LOCAL virtual void doChangeLanguage() ST_ATTR_OVERRIDE { updateStrings(); }
52
53
+ /**
54
+ * Return HMD framerate.
55
+ */
56
+ ST_LOCAL virtual float getMaximumTargetFps() const ST_ATTR_OVERRIDE;
57
+
58
private:
59
60
/**
61
62
&& myDevice == DEVICE_HMD;
63
}
64
65
+ /**
66
+ * Retrieve active head position.
67
+ */
68
+ ST_LOCAL void updateVRProjectionFrustums();
69
+
70
private:
71
72
static StAtomic<int32_t> myInstancesNb; //!< shared counter for all instances
73
74
double myVrMarginsBottom;
75
double myVrMarginsLeft;
76
double myVrMarginsRight;
77
- int myVrRendSizeX; //!< FBO width for rendering into VR (can be greater then actual HMD resolution to compensate distortion)
78
- int myVrRendSizeY; //!< FBO height for rendering into VR
79
+ StRectF_t myVrFrustumL; //!< projection frustum for the left eye
80
+ StRectF_t myVrFrustumR; //!< projection frustum for the right eye
81
+ StVec2<int> myVrRendSize; //!< FBO width x height for rendering into VR (can be greater then actual HMD resolution to compensate distortion)
82
+ float myVrFrequency; //!< display frequency
83
+ float myVrAspectRatio; //!< aspect ratio
84
+ float myVrFieldOfView; //!< field of view
85
+ float myVrIOD; //!< intra-ocular distance in meters
86
bool myVrTrackOrient; //!< track orientation flag
87
bool myVrToDrawMsg;
88
StHandle<StGLTextureQuad> myVrFullscreenMsg;
89
90
#ifdef ST_HAVE_OPENVR
91
vr::IVRSystem* myVrHmd; //!< OpenVR session object
92
vr::TrackedDevicePose_t* myVrTrackedPoses; //!< array of tracked devices poses
93
-#elif defined(ST_HAVE_LIBOVR)
94
- ovrSession myVrHmd;
95
- ovrSwapTextureSet* myOvrSwapTexture;
96
- GLuint myOvrSwapFbo[2];
97
- ovrGLTexture* myOvrMirrorTexture;
98
- GLuint myOvrMirrorFbo;
99
#endif
100
101
bool myToShowCursor; //!< cursor visibility flag
102
sview-17_04.tar.gz/StOutDistorted/StOutDistorted.rc -> sview-20_08.tar.gz/StOutDistorted/StOutDistorted.rc
Changed
10
1
2
BEGIN
3
VALUE "FileDescription", "Stereo Distorted Renderer library\000"
4
VALUE "FileVersion", SVIEW_SDK_VER_STRING "\000"
5
- VALUE "LegalCopyright", "\251 2013-2017 Kirill Gavrilov\000"
6
+ VALUE "LegalCopyright", "\251 2013-2020 Kirill Gavrilov and sView developers\000"
7
VALUE "ProductName", "StOutDistorted\000"
8
VALUE "ProductVersion", SVIEW_SDK_VER_STRING "\000"
9
VALUE "OfficialSite", "www.sview.ru\000"
10
sview-20_08.tar.gz/StOutDistorted/lang/spanish
Added
2
1
+(directory)
2
sview-20_08.tar.gz/StOutDistorted/lang/spanish/StOutDistorted.lng
Added
19
1
2
+# Spanish translation file for StOutDistorted
3
+--------
4
+1000=TV (par paralelo)
5
+1001=Salida distorsionada
6
+1002=OpenVR HMD
7
+1003=Distorsión de barril
8
+1110=Disposición
9
+1111=Adyacente
10
+1112=Arriba y abajo
11
+1113=Paralela (anamórfica)
12
+1114=Arriba y abajo (anamórfica)
13
+1120=Distorsión
14
+1121=Ninguna
15
+1123=Mostrar mono en estéreo
16
+2000=sView - Módulo de salida distorsionada
17
+2001=versión
18
+2002=© {0} Kirill Gavrilov <{1}>\nSitio oficial: {2}
19
sview-17_04.tar.gz/StOutDual/StOutDual.cpp -> sview-20_08.tar.gz/StOutDual/StOutDual.cpp
Changed
10
1
2
StString& aDescr = aLangMap.changeValueId(STTR_PLUGIN_DESCRIPTION,
3
"(C) {0} Kirill Gavrilov <{1}>\nOfficial site: {2}\n\nThis library is distributed under LGPL3.0");
4
myAbout = aTitle + '\n' + aVerString + " " + StVersionInfo::getSDKVersionString() + "\n \n"
5
- + aDescr.format("2007-2017", "kirill@sview.ru", "www.sview.ru");
6
+ + aDescr.format("2007-2020", "kirill@sview.ru", "www.sview.ru");
7
}
8
9
StOutDual::StOutDual(const StHandle<StResourceManager>& theResMgr,
10
sview-17_04.tar.gz/StOutDual/StOutDual.rc -> sview-20_08.tar.gz/StOutDual/StOutDual.rc
Changed
10
1
2
BEGIN
3
VALUE "FileDescription", "Stereo Dual Renderer library\000"
4
VALUE "FileVersion", SVIEW_SDK_VER_STRING "\000"
5
- VALUE "LegalCopyright", "\251 2007-2017 Kirill Gavrilov\000"
6
+ VALUE "LegalCopyright", "\251 2007-2020 Kirill Gavrilov and sView developers\000"
7
VALUE "ProductName", "StOutDual\000"
8
VALUE "ProductVersion", SVIEW_SDK_VER_STRING "\000"
9
VALUE "OfficialSite", "www.sview.ru\000"
10
sview-20_08.tar.gz/StOutDual/lang/spanish
Added
2
1
+(directory)
2
sview-20_08.tar.gz/StOutDual/lang/spanish/StOutDual.lng
Added
13
1
2
+# Spanish translation file for StOutDual
3
+--------
4
+1000=Salida dual
5
+1001=Dispositivo estéreo con entrada dual: algunos HMD, monitores estéreo reflejados, proyectores duales
6
+1002=Salida espejo
7
+1003=Monitores estéreo reflejados hechos a mano (espejo en la dirección X)
8
+1102=Monitor esclavo
9
+1103=Mostrar mono en estéreo
10
+2000=sView - Módulo de salida dual
11
+2001=versión
12
+2002=© {0} Kirill Gavrilov <{1}>\nSitio oficial: {2}
13
sview-17_04.tar.gz/StOutIZ3D/StOutIZ3D.cpp -> sview-20_08.tar.gz/StOutIZ3D/StOutIZ3D.cpp
Changed
10
1
2
StString& aDescr = aLangMap.changeValueId(STTR_PLUGIN_DESCRIPTION,
3
"(C) {0} Kirill Gavrilov <{1}>\nOfficial site: {2}\n\nThis library is distributed under LGPL3.0");
4
myAbout = aTitle + '\n' + aVerString + " " + StVersionInfo::getSDKVersionString() + "\n \n"
5
- + aDescr.format("2009-2017", "kirill@sview.ru", "www.sview.ru");
6
+ + aDescr.format("2009-2020", "kirill@sview.ru", "www.sview.ru");
7
}
8
9
StOutIZ3D::StOutIZ3D(const StHandle<StResourceManager>& theResMgr,
10
sview-17_04.tar.gz/StOutIZ3D/StOutIZ3D.rc -> sview-20_08.tar.gz/StOutIZ3D/StOutIZ3D.rc
Changed
10
1
2
BEGIN
3
VALUE "FileDescription", "IZ3D Renderer library\000"
4
VALUE "FileVersion", SVIEW_SDK_VER_STRING "\000"
5
- VALUE "LegalCopyright", "\251 2009-2017 Kirill Gavrilov. Copyright \251 iZ3D LLC. All rights for codes for iZ3D conversion reserved for iZ3D LLC 2007-2009\000"
6
+ VALUE "LegalCopyright", "\251 2009-2020 Kirill Gavrilov. Copyright \251 iZ3D LLC. All rights for codes for iZ3D conversion reserved for iZ3D LLC 2007-2009\000"
7
VALUE "ProductName", "StOutIZ3D\000"
8
VALUE "ProductVersion", SVIEW_SDK_VER_STRING "\000"
9
VALUE "OfficialSite", "www.sview.ru\000"
10
sview-20_08.tar.gz/StOutIZ3D/lang/spanish
Added
2
1
+(directory)
2
sview-20_08.tar.gz/StOutIZ3D/lang/spanish/StOutIZ3D.lng
Added
13
1
2
+# Spanish translation file for StOutIZ3D
3
+--------
4
+1000=Visualización IZ3D
5
+1001=Visualización IZ3D
6
+1102=Gafas iZ3D
7
+1120=Clásico
8
+1121=Moderno
9
+1122=Clásico (rápido)
10
+2000=sView - Módulo de salida iZ3D
11
+2001=versión
12
+2002=© {0} Kirill Gavrilov <{1}>\n© 2007-2009 iZ3D LLC\nSitio oficial: {2}\nSitio iZ3D LLC: www.iz3d.com
13
sview-17_04.tar.gz/StOutInterlace/StOutInterlace.cpp -> sview-20_08.tar.gz/StOutInterlace/StOutInterlace.cpp
Changed
484
1
2
#include <StImage/StImagePlane.h>
3
#include <StVersion.h>
4
5
+#include <fstream>
6
+
7
namespace {
8
9
static const char ST_OUT_PLUGIN_NAME[] = "StOutInterlace";
10
11
struct StMonInterlacedInfo_t {
12
const stUtf8_t* pnpid;
13
bool isReversed;
14
+ bool isRowInterlaced;
15
};
16
17
/**
18
* Database of known interlaced monitors.
19
*/
20
static const StMonInterlacedInfo_t THE_KNOWN_MONITORS[] = {
21
- {"ZMT1900", false}, // Zalman Trimon M190S
22
- {"ZMT2200", false}, // Zalman Trimon M220W
23
- {"ENV2373", true }, // Envision
24
- {"HIT8002", false}, // Hyundai W220S D-Sub
25
- {"HIT8D02", false}, // Hyundai W220S DVID
26
- {"HIT7003", false}, // Hyundai W240S D-Sub
27
- {"HIT7D03", false}, // Hyundai W240S D-Sub
28
- //{"ACI23C2", false}, // ASUS VG23AH
29
- {"ACI27C2", false}, // ASUS VG27AH
30
- { "", false} // NULL-terminate array
31
+ {"ZMT1900", false, true}, // Zalman Trimon M190S
32
+ {"ZMT2200", false, true}, // Zalman Trimon M220W
33
+ {"ENV2373", true , true}, // Envision
34
+ {"HIT8002", false, true}, // Hyundai W220S D-Sub
35
+ {"HIT8D02", false, true}, // Hyundai W220S DVID
36
+ {"HIT7003", false, true}, // Hyundai W240S D-Sub
37
+ {"HIT7D03", false, true}, // Hyundai W240S D-Sub
38
+ {"ACI23D3", false, true}, // ASUS VG23AH
39
+ {"ACI27C2", false, true}, // ASUS VG27AH
40
+ //
41
+ {"ST@COL0", false, false}, // Android devices with parallel barrier (column-interleaved)
42
+ { "", false, false} // NULL-terminate array
43
};
44
45
+#if defined(__ANDROID__)
46
+ // Truly / Freevi / Commander activation
47
+ namespace mi3d_tn {
48
+ static const char* CTRL_FILE = "/dev/mi3d_tn_ctrl";
49
+ enum {
50
+ SET_TN_OFF = 16,
51
+ SET_VERTICAL_TN_ON = 32,
52
+ SET_HORIZONTAL_TN_ON = 64,
53
+ GET_TN_STATUS = 128,
54
+ };
55
+ }
56
+#endif
57
+
58
// translation resources
59
enum {
60
STTR_HINTERLACE_NAME = 1000,
61
62
static const StGLVarLocation ST_VATTRIB_VERTEX(0);
63
static const StGLVarLocation ST_VATTRIB_TCOORD(1);
64
65
+ inline bool isInterlacedMonitor(const StMonitor& theMon,
66
+ bool& theIsReversed,
67
+ bool& theIsRowInterlaced) {
68
+ if(theMon.getPnPId().getSize() != 7) {
69
+ return false;
70
+ }
71
+ for(size_t anIter = 0;; ++anIter) {
72
+ const StMonInterlacedInfo_t& aMon = THE_KNOWN_MONITORS[anIter];
73
+ if(aMon.pnpid[0] == '\0') {
74
+ return false;
75
+ } else if(stAreEqual(aMon.pnpid, theMon.getPnPId().toCString(), 7)) {
76
+ theIsReversed = aMon.isReversed;
77
+ theIsRowInterlaced = aMon.isRowInterlaced;
78
+ return true;
79
+ }
80
+ }
81
+ }
82
+
83
}
84
85
StProgramFB::StProgramFB(const StString& theTitle)
86
87
88
StAtomic<int32_t> StOutInterlace::myInstancesNb(0);
89
90
-inline bool isInterlacedMonitor(const StMonitor& theMon,
91
- bool& theIsReversed) {
92
- if(theMon.getPnPId().getSize() != 7) {
93
- return false;
94
- }
95
- for(size_t anIter = 0;; ++anIter) {
96
- const StMonInterlacedInfo_t& aMon = THE_KNOWN_MONITORS[anIter];
97
- if(aMon.pnpid[0] == '\0') {
98
- return false;
99
- } else if(stAreEqual(aMon.pnpid, theMon.getPnPId().toCString(), 7)) {
100
- theIsReversed = aMon.isReversed;
101
- return true;
102
- }
103
- }
104
-}
105
-
106
-StHandle<StMonitor> StOutInterlace::getHInterlaceMonitor(const StArrayList<StMonitor>& theMonitors,
107
- bool& theIsReversed) {
108
+StHandle<StMonitor> StOutInterlace::getInterlacedMonitor(const StArrayList<StMonitor>& theMonitors,
109
+ bool& theIsReversed,
110
+ bool& theIsRowInterlaced) {
111
for(size_t aMonIter = 0; aMonIter < theMonitors.size(); ++aMonIter) {
112
const StMonitor& aMon = theMonitors[aMonIter];
113
- if(isInterlacedMonitor(aMon, theIsReversed)) {
114
+ if(isInterlacedMonitor(aMon, theIsReversed, theIsRowInterlaced)) {
115
return new StMonitor(aMon);
116
}
117
}
118
119
120
const char* StOutInterlace::getDeviceId() const {
121
switch(myDevice) {
122
- case DEVICE_COL_INTERLACED: return "Col";
123
- case DEVICE_CHESSBOARD: return "Chess";
124
- case DEVICE_ROW_INTERLACED_ED: return "RowED";
125
+ case DEVICE_COL_INTERLACED: return "Col";
126
+ case DEVICE_COL_INTERLACED_MI3D: return "ColMI3D";
127
+ case DEVICE_CHESSBOARD: return "Chess";
128
+ case DEVICE_ROW_INTERLACED_ED: return "RowED";
129
case DEVICE_ROW_INTERLACED:
130
- default: return "Row";
131
+ default: return "Row";
132
}
133
}
134
135
136
myDevice = DEVICE_ROW_INTERLACED;
137
} else if(theDevice == "Col") {
138
myDevice = DEVICE_COL_INTERLACED;
139
+ } else if(theDevice == "ColMI3D") {
140
+ myDevice = DEVICE_COL_INTERLACED_MI3D;
141
} else if(theDevice == "Chess") {
142
myDevice = DEVICE_CHESSBOARD;
143
} else if(theDevice == "RowED") {
144
145
146
void StOutInterlace::getDevices(StOutDevicesList& theList) const {
147
for(size_t anIter = 0; anIter < myDevices.size(); ++anIter) {
148
+ if(myDevices[anIter]->Priority == ST_DEVICE_SUPPORT_IGNORE) {
149
+ continue;
150
+ }
151
theList.add(myDevices[anIter]);
152
}
153
}
154
155
myDevices[DEVICE_ROW_INTERLACED] ->Desc = aLangMap.changeValueId(STTR_HINTERLACE_DESC, "Row interlaced displays: Zalman, Hyundai,...");
156
myDevices[DEVICE_COL_INTERLACED] ->Name = aLangMap.changeValueId(STTR_VINTERLACE_NAME, "Column Interlaced");
157
myDevices[DEVICE_COL_INTERLACED] ->Desc = aLangMap.changeValueId(STTR_VINTERLACE_DESC, "Column interlaced displays");
158
-#if !defined(__ANDROID__)
159
myDevices[DEVICE_CHESSBOARD] ->Name = aLangMap.changeValueId(STTR_CHESSBOARD_NAME, "DLP TV (chessboard)");
160
myDevices[DEVICE_CHESSBOARD] ->Desc = aLangMap.changeValueId(STTR_CHESSBOARD_DESC, "DLP TV (chessboard)");
161
myDevices[DEVICE_ROW_INTERLACED_ED]->Name = aLangMap.changeValueId(STTR_HINTERLACE_ED_NAME, "Interlaced ED");
162
myDevices[DEVICE_ROW_INTERLACED_ED]->Desc = aLangMap.changeValueId(STTR_HINTERLACE_ED_DESC, "EDimensional in interlaced mode");
163
-#endif
164
+ myDevices[DEVICE_COL_INTERLACED_MI3D]->Name = "Interlaced [MI3D]";
165
+ myDevices[DEVICE_COL_INTERLACED_MI3D]->Desc = "Interlaced display with parallel barrier";
166
+
167
params.ToReverse->setName(aLangMap.changeValueId(STTR_PARAMETER_REVERSE, "Reverse Order"));
168
params.BindToMon->setName(aLangMap.changeValueId(STTR_PARAMETER_BIND_MON, "Bind To Supported Monitor"));
169
params.ToUseMask->setName(aLangMap.changeValueId(STTR_PARAMETER_USE_MASK, "Use texture mask (compatibility)"));
170
171
StString& aDescr = aLangMap.changeValueId(STTR_PLUGIN_DESCRIPTION,
172
"(C) {0} Kirill Gavrilov <{1}>\nOfficial site: {2}\n\nThis library is distributed under LGPL3.0");
173
myAbout = aTitle + '\n' + aVerString + " " + StVersionInfo::getSDKVersionString() + "\n \n"
174
- + aDescr.format("2009-2017", "kirill@sview.ru", "www.sview.ru");
175
+ + aDescr.format("2009-2020", "kirill@sview.ru", "www.sview.ru");
176
}
177
178
StOutInterlace::StOutInterlace(const StHandle<StResourceManager>& theResMgr,
179
180
myTexMaskDevice(DEVICE_AUTO),
181
myTexMaskReversed(false),
182
myDevice(DEVICE_AUTO),
183
+ myBarrierState(BarrierState_Unknown),
184
myEDTimer(true),
185
myEDIntelaceOn(new StGLProgram("ED Interlace On")),
186
myEDOff(new StGLProgram("ED Interlace Off")),
187
188
myGlPrograms[DEVICE_COL_INTERLACED] = new StProgramFB("Column Interlace");
189
myGlPrograms[DEVICE_CHESSBOARD] = new StProgramFB("Chessboard");
190
myGlPrograms[DEVICE_ROW_INTERLACED_ED] = myGlPrograms[DEVICE_ROW_INTERLACED];
191
+ myGlPrograms[DEVICE_COL_INTERLACED_MI3D] = myGlPrograms[DEVICE_COL_INTERLACED];
192
193
- myGlProgramsRev[DEVICE_ROW_INTERLACED] = new StProgramFB("Row Interlace Inversed");
194
- myGlProgramsRev[DEVICE_COL_INTERLACED] = new StProgramFB("Column Interlace Inversed");
195
- myGlProgramsRev[DEVICE_CHESSBOARD] = new StProgramFB("Chessboard Inversed");
196
- myGlProgramsRev[DEVICE_ROW_INTERLACED_ED] = myGlProgramsRev[DEVICE_ROW_INTERLACED];
197
+ myGlProgramsRev[DEVICE_ROW_INTERLACED] = new StProgramFB("Row Interlace Inversed");
198
+ myGlProgramsRev[DEVICE_COL_INTERLACED] = new StProgramFB("Column Interlace Inversed");
199
+ myGlProgramsRev[DEVICE_CHESSBOARD] = new StProgramFB("Chessboard Inversed");
200
+ myGlProgramsRev[DEVICE_ROW_INTERLACED_ED] = myGlProgramsRev[DEVICE_ROW_INTERLACED];
201
+ myGlProgramsRev[DEVICE_COL_INTERLACED_MI3D] = myGlProgramsRev[DEVICE_COL_INTERLACED];
202
203
myGlProgramMask = new StProgramFB("Interlace Mask");
204
205
206
aDevCol->Name = stCString("Column Interlaced");
207
myDevices.add(aDevCol);
208
209
-#if !defined(__ANDROID__)
210
StHandle<StOutDevice> aDevChess = new StOutDevice();
211
aDevChess->PluginId = ST_OUT_PLUGIN_NAME;
212
aDevChess->DeviceId = stCString("Chess");
213
+#if defined(__ANDROID__)
214
+ aDevChess->Priority = ST_DEVICE_SUPPORT_IGNORE;
215
+#else
216
aDevChess->Priority = ST_DEVICE_SUPPORT_NONE;
217
+#endif
218
aDevChess->Name = stCString("DLP TV (chessboard)");
219
myDevices.add(aDevChess);
220
221
StHandle<StOutDevice> aDevED = new StOutDevice();
222
aDevED->PluginId = ST_OUT_PLUGIN_NAME;
223
aDevED->DeviceId = stCString("RowED");
224
+#if defined(__ANDROID__)
225
+ aDevED->Priority = ST_DEVICE_SUPPORT_IGNORE;
226
+#else
227
aDevED->Priority = ST_DEVICE_SUPPORT_NONE;
228
+#endif
229
aDevED->Name = stCString("Interlaced ED");
230
myDevices.add(aDevED);
231
+
232
+ StHandle<StOutDevice> aDevMI3D = new StOutDevice();
233
+ aDevMI3D->PluginId = ST_OUT_PLUGIN_NAME;
234
+ aDevMI3D->DeviceId = stCString("ColMI3D");
235
+ aDevMI3D->Priority = ST_DEVICE_SUPPORT_IGNORE;
236
+#if defined(__ANDROID__)
237
+ {
238
+ std::fstream aCtrlFile;
239
+ aCtrlFile.open(mi3d_tn::CTRL_FILE, std::ios_base::in);
240
+ if(aCtrlFile.is_open()) {
241
+ aCtrlFile.close();
242
+ aDevMI3D->Priority = ST_DEVICE_SUPPORT_PREFER;
243
+ setBarrierState(BarrierState_Off);
244
+ }
245
+ }
246
#endif
247
+ aDevMI3D->Name = stCString("Interlaced [MI3D]");
248
+ myDevices.add(aDevMI3D);
249
250
// detect connected displays
251
- bool isDummyReversed= false;
252
- StHandle<StMonitor> aMonInterlaced = StOutInterlace::getHInterlaceMonitor(aMonitors, isDummyReversed);
253
+ bool isDummyReversed = false;
254
+ bool isRowInterlaced = false;
255
+ StHandle<StMonitor> aMonInterlaced = getInterlacedMonitor(aMonitors, isDummyReversed, isRowInterlaced);
256
if(!aMonInterlaced.isNull()) {
257
- aDevRow->Priority = ST_DEVICE_SUPPORT_PREFER;
258
+ if(isRowInterlaced) {
259
+ aDevRow->Priority = ST_DEVICE_SUPPORT_PREFER;
260
+ } else {
261
+ aDevCol->Priority = ST_DEVICE_SUPPORT_PREFER;
262
+ }
263
}
264
265
// options
266
267
StMonitor aMonitor = aMonitors[aRect.center()];
268
if(params.BindToMon->getValue()
269
&& !aMonInterlaced.isNull()
270
- && !isInterlacedMonitor(aMonitor, isDummyReversed)) {
271
+ && !isInterlacedMonitor(aMonitor, isDummyReversed, isRowInterlaced)) {
272
aMonitor = *aMonInterlaced;
273
}
274
if(isLoadedPosition) {
275
276
if(!aMonInterlaced.isNull()) {
277
myIsMonReversed = false;
278
StMonitor aMonitor = aMonitors[StWindow::getPlacement().center()];
279
- isInterlacedMonitor(aMonitor, myIsMonReversed);
280
+ isInterlacedMonitor(aMonitor, myIsMonReversed, isRowInterlaced);
281
}
282
283
// load device settings
284
mySettings->loadInt32(ST_SETTING_DEVICE_ID, myDevice);
285
- if(myDevice == DEVICE_AUTO) {
286
+ if(myDevice == DEVICE_AUTO
287
+ || myDevice >= (int )myDevices.size()
288
+ || myDevices[myDevice]->Priority == ST_DEVICE_SUPPORT_IGNORE) {
289
myDevice = DEVICE_ROW_INTERLACED;
290
}
291
292
293
releaseResources();
294
}
295
296
+void StOutInterlace::setBarrierState(BarrierState theBarrierState) {
297
+ if(myBarrierState == theBarrierState) {
298
+ return;
299
+ }
300
+
301
+ myBarrierState = theBarrierState;
302
+#if defined(__ANDROID__)
303
+ unsigned char aValue = mi3d_tn::SET_TN_OFF;
304
+ switch(myBarrierState) {
305
+ case BarrierState_Unknown:
306
+ case BarrierState_Off:
307
+ aValue = mi3d_tn::SET_TN_OFF;
308
+ break;
309
+ case BarrierState_Landscape:
310
+ aValue = mi3d_tn::SET_VERTICAL_TN_ON;
311
+ break;
312
+ case BarrierState_Portrait:
313
+ aValue = mi3d_tn::SET_HORIZONTAL_TN_ON;
314
+ break;
315
+ }
316
+ std::fstream aCtrlFile;
317
+ aCtrlFile.open(mi3d_tn::CTRL_FILE);
318
+ if(aCtrlFile.is_open()) {
319
+ aCtrlFile << aValue;
320
+ aCtrlFile.close();
321
+ }
322
+#endif
323
+}
324
+
325
void StOutInterlace::close() {
326
StWindow::params.VSyncMode->signals.onChanged -= stSlot(this, &StOutInterlace::doSwitchVSync);
327
beforeClose();
328
329
StThread::sleep(10);
330
}
331
}
332
+ setBarrierState(BarrierState_Off);
333
}
334
335
void StOutInterlace::show() {
336
337
// discard mask texture
338
StGLFragmentShader aShaderMask(myGlProgramMask->getTitle());
339
StGLAutoRelease aTmp8(*myContext, aShaderMask);
340
- if(!aShaderMask.init(*myContext,
341
- "uniform sampler2D uTexture;\n"
342
- "uniform sampler2D uMaskTexture;\n"
343
- "varying vec2 fTexCoord;\n"
344
- "void main(void) {\n"
345
- " float aMask = texture2D(uMaskTexture, fTexCoord).a;\n"
346
- " if(aMask < 0.5) { discard; }\n"
347
- " gl_FragColor = texture2D(uTexture, fTexCoord);\n"
348
- "}\n")) {
349
+
350
+ const char* FRAGMENT_GET_ALPHA = myContext->arbTexRG
351
+ ? "#define stTextureAlpha(theSampler, theCoords) texture2D(theSampler, theCoords).r\n"
352
+ : "#define stTextureAlpha(theSampler, theCoords) texture2D(theSampler, theCoords).a\n";
353
+ const StString aMaskProgram = StString() + FRAGMENT_GET_ALPHA
354
+ + "uniform sampler2D uTexture;\n"
355
+ "uniform sampler2D uMaskTexture;\n"
356
+ "varying vec2 fTexCoord;\n"
357
+ "void main(void) {\n"
358
+ " float aMask = stTextureAlpha(uMaskTexture, fTexCoord);\n"
359
+ " if(aMask < 0.5) { discard; }\n"
360
+ " gl_FragColor = texture2D(uTexture, fTexCoord);\n"
361
+ "}\n";
362
+
363
+ if(!aShaderMask.init(*myContext, aMaskProgram.toCString())) {
364
myMsgQueue->pushError(aShadersError);
365
myIsBroken = true;
366
return true;
367
368
// note that this enumeration is not enough to handle rotation direction,
369
// which is required to automatically swap lines/columns order)
370
myIsMonPortrait = aMon.getOrientation() == StMonitor::Orientation_Portrait;
371
- isInterlacedMonitor(aMon, myIsMonReversed);
372
+ bool isRowInterlaced;
373
+ isInterlacedMonitor(aMon, myIsMonReversed, isRowInterlaced);
374
}
375
376
void StOutInterlace::processEvents() {
377
378
}
379
break;
380
}
381
+ case DEVICE_COL_INTERLACED_MI3D:
382
case DEVICE_COL_INTERLACED: {
383
if(theToReverse) {
384
*aPixel = (aColIter % 2 == 0) ? 255 : 0;
385
386
}
387
}
388
389
+ const GLint aTexFormat = myContext->arbTexRG ? GL_R8 : GL_ALPHA;
390
+ if(myTextureMask->getTextureFormat() != aTexFormat) {
391
+ myTextureMask->setTextureFormat(aTexFormat);
392
+ }
393
+
394
if(!myTextureMask->init(*myContext, anImage)) {
395
myMsgQueue->pushError(stCString("Interlace output - critical error:\nMask texture resize failed!"));
396
myIsBroken = true;
397
398
myContext->stglResizeViewport(aVPort);
399
StWindow::signals.onRedraw(ST_DRAW_LEFT);
400
401
+ if(myIsFirstDraw) {
402
+ myIsFirstDraw = false;
403
+
404
+ // fall-back on known problematic devices
405
+ const StString aGlRenderer((const char* )myContext->core11fwd->glGetString(GL_RENDERER));
406
+ if(aGlRenderer.isContains(stCString("PowerVR Rogue G6200"))) {
407
+ params.ToUseMask->setValue(true);
408
+ }
409
+ }
410
+
411
if(!StWindow::isStereoOutput() || myIsBroken) {
412
if(myToCompressMem) {
413
myFrmBuffer->release(*myContext);
414
415
}
416
}
417
stglDrawEDCodes();
418
+ } else if(myDevice == DEVICE_COL_INTERLACED_MI3D) {
419
+ setBarrierState(BarrierState_Off);
420
}
421
422
// decrease FPS to target by thread sleeps
423
424
return;
425
}
426
427
- if(myIsFirstDraw) {
428
- myIsFirstDraw = false;
429
-
430
- // fall-back on known problematic devices
431
- const StString aGlRenderer((const char* )myContext->core11fwd->glGetString(GL_RENDERER));
432
- if(aGlRenderer.isContains(stCString("PowerVR Rogue G6200"))) {
433
- params.ToUseMask->setValue(true);
434
- }
435
- }
436
-
437
// reverse L/R according to window position
438
bool isPixelReverse = false;
439
const StRectI_t aWinRect = StWindow::getPlacement();
440
441
int aDevice = myDevice;
442
443
// handle portrait orientation
444
- if(myIsMonPortrait) {
445
+ if(myDevice == DEVICE_COL_INTERLACED_MI3D) {
446
+ aDevice = DEVICE_COL_INTERLACED;
447
+ } else if(myIsMonPortrait) {
448
switch(myDevice) {
449
case DEVICE_ROW_INTERLACED:
450
aDevice = DEVICE_COL_INTERLACED;
451
452
switch(aDevice) {
453
case DEVICE_CHESSBOARD:
454
case DEVICE_COL_INTERLACED:
455
+ case DEVICE_COL_INTERLACED_MI3D:
456
isPixelReverse = !isPixelReverse; break;
457
}
458
}
459
460
}
461
}
462
stglDrawEDCodes();
463
+ } else if(myDevice == DEVICE_COL_INTERLACED_MI3D) {
464
+ setBarrierState(myIsMonPortrait ? BarrierState_Portrait : BarrierState_Landscape);
465
}
466
467
// decrease FPS to target by thread sleeps
468
469
const StSearchMonitors& aMonitors = StWindow::getMonitors();
470
StRectI_t aRect = StWindow::getPlacement();
471
StMonitor aMon = aMonitors[aRect.center()];
472
- if(isInterlacedMonitor(aMon, myIsMonReversed)
473
+ bool isRowInterlaced = false;
474
+ if(isInterlacedMonitor(aMon, myIsMonReversed, isRowInterlaced)
475
|| !isMovable()) {
476
return;
477
}
478
479
- StHandle<StMonitor> anInterlacedMon = StOutInterlace::getHInterlaceMonitor(aMonitors, myIsMonReversed);
480
+ StHandle<StMonitor> anInterlacedMon = getInterlacedMonitor(aMonitors, myIsMonReversed, isRowInterlaced);
481
if(anInterlacedMon.isNull()) {
482
return;
483
}
484
sview-17_04.tar.gz/StOutInterlace/StOutInterlace.h -> sview-20_08.tar.gz/StOutInterlace/StOutInterlace.h
Changed
63
1
2
private:
3
4
enum {
5
- DEVICE_AUTO =-1,
6
- DEVICE_ROW_INTERLACED = 0, //!< interlace (horizontal 1xPixel lines, full color from R or L)
7
- DEVICE_COL_INTERLACED = 1, //!< interlace (vertical 1xPixel lines, full color from R or L)
8
- DEVICE_CHESSBOARD = 2, //!< 1xPixel chessboard (some DLP devices)
9
- DEVICE_ROW_INTERLACED_ED = 3, //!< interlace (horizontal 1xPixel lines) + EDimensional onscreen codes
10
+ DEVICE_AUTO =-1,
11
+ DEVICE_ROW_INTERLACED = 0, //!< interlace (horizontal 1xPixel lines, full color from R or L)
12
+ DEVICE_COL_INTERLACED = 1, //!< interlace (vertical 1xPixel lines, full color from R or L)
13
+ DEVICE_CHESSBOARD = 2, //!< 1xPixel chessboard (some DLP devices)
14
+ DEVICE_ROW_INTERLACED_ED = 3, //!< interlace (horizontal 1xPixel lines) + EDimensional onscreen codes
15
+ DEVICE_COL_INTERLACED_MI3D = 4, //!< interlace with barrier
16
17
DEVICE_NB,
18
};
19
20
private:
21
22
- ST_LOCAL static StHandle<StMonitor> getHInterlaceMonitor(const StArrayList<StMonitor>& theMonitors,
23
- bool& theIsReversed);
24
+ /**
25
+ * Look for interlaced monitors within the given list.
26
+ */
27
+ ST_LOCAL static StHandle<StMonitor> getInterlacedMonitor(const StArrayList<StMonitor>& theMonitors,
28
+ bool& theIsReversed,
29
+ bool& theIsRowInterlaced);
30
31
ST_LOCAL void stglDrawEDCodes();
32
33
34
35
} params;
36
37
+ /**
38
+ * Parallax barrier state.
39
+ */
40
+ enum BarrierState {
41
+ BarrierState_Unknown = -1,
42
+ BarrierState_Off = 0,
43
+ BarrierState_Landscape,
44
+ BarrierState_Portrait,
45
+ };
46
+
47
+ /**
48
+ * Initialize parallax barrier state.
49
+ */
50
+ void setBarrierState(BarrierState theBarrierState);
51
+
52
private:
53
54
StOutDevicesList myDevices;
55
56
StGLVertexBuffer myQuadTexCoordBuf;
57
int myDevice;
58
StHandle<StMonitor> myMonitor; //!< current monitor
59
+ BarrierState myBarrierState;
60
61
StRectI_t myWinRect;
62
StRectI_t myEDRect;
63
sview-17_04.tar.gz/StOutInterlace/StOutInterlace.rc -> sview-20_08.tar.gz/StOutInterlace/StOutInterlace.rc
Changed
10
1
2
BEGIN
3
VALUE "FileDescription", "Interlace Renderer library\000"
4
VALUE "FileVersion", SVIEW_SDK_VER_STRING "\000"
5
- VALUE "LegalCopyright", "\251 2009-2017 Kirill Gavrilov\000"
6
+ VALUE "LegalCopyright", "\251 2009-2020 Kirill Gavrilov and sView developers\000"
7
VALUE "ProductName", "StOutInterlace\000"
8
VALUE "ProductVersion", SVIEW_SDK_VER_STRING "\000"
9
VALUE "OfficialSite", "www.sview.ru\000"
10
sview-20_08.tar.gz/StOutInterlace/lang/spanish
Added
2
1
+(directory)
2
sview-20_08.tar.gz/StOutInterlace/lang/spanish/StOutInterlace.lng
Added
18
1
2
+# Spanish translation file for StOutInterlaced
3
+--------
4
+1000=Filas entrelazadas
5
+1001=Pantallas con filas entrelazadas: Zalman, Hyundai...
6
+1002=Columnas entrelazadas
7
+1003=Pantallas con columnas entrelazadas
8
+1006=DLP TV (tablero de ajedrez)
9
+1007=DLP TV (tablero de ajedrez)
10
+1008=ED entrelazado
11
+1009=EDimensional en modo entrelazado
12
+1102=Orden inverso
13
+1103=Enlazar con monitor compatible
14
+1104=Usar máscara de textura (compatibilidad)
15
+2000=sView - Módulo de salida entrelazada
16
+2001=versión
17
+2002=© {0} Kirill Gavrilov <{1}>\nSitio oficial: {2}
18
sview-17_04.tar.gz/StOutPageFlip/StDXNVWindow.cpp -> sview-20_08.tar.gz/StOutPageFlip/StDXNVWindow.cpp
Changed
35
1
2
LPARAM theParamL) {
3
// we do stupid checks here...
4
if(myStWin->isFullScreen() && myStWin->isStereoOutput()) {
5
- if(theMsg == WM_MOUSEWHEEL) {
6
- int zDelta = GET_WHEEL_DELTA_WPARAM(theParamW);
7
+ if(theMsg == WM_MOUSEWHEEL
8
+ || theMsg == WM_MOUSEHWHEEL) {
9
+ const bool isVert = (theMsg == WM_MOUSEWHEEL);
10
+ const int aZDelta = GET_WHEEL_DELTA_WPARAM(theParamW);
11
+ const int aNbSteps = (aZDelta > 0) ? 1 : -1;
12
+ const float aDeltaSt = float(aZDelta) / float(WHEEL_DELTA);
13
const StPointD_t aPnt = myStWin->getMousePos();
14
StEvent anEvent;
15
- anEvent.Type = stEvent_Scroll;
16
- anEvent.Scroll.Time = 0.0; //getEventTime(myEvent.time);
17
- anEvent.Scroll.PointX = aPnt.x();
18
- anEvent.Scroll.PointY = aPnt.y();
19
- anEvent.Scroll.StepsX = 0;
20
- anEvent.Scroll.StepsY = (zDelta > 0) ? 1 : -1;
21
- anEvent.Scroll.DeltaX = 0.0;
22
- anEvent.Scroll.DeltaY = 10.0f * anEvent.Scroll.StepsY;
23
- anEvent.Scroll.IsFromMultiTouch = false;
24
+ anEvent.Scroll.init(0.0, //getEventTime(myEvent.time);
25
+ aPnt.x(),
26
+ aPnt.y(),
27
+ !isVert ? aDeltaSt : 0.0f,
28
+ isVert ? aDeltaSt : 0.0f,
29
+ false);
30
+ anEvent.Scroll.StepsX = !isVert ? aNbSteps : 0;
31
+ anEvent.Scroll.StepsY = isVert ? aNbSteps : 0;
32
myStWin->post(anEvent);
33
}
34
35
sview-17_04.tar.gz/StOutPageFlip/StOutPageFlip.cpp -> sview-20_08.tar.gz/StOutPageFlip/StOutPageFlip.cpp
Changed
56
1
2
3
static StMonitor getHigestFreqMonitor(const StSearchMonitors& theMonitors) {
4
size_t hfreqMon = 0;
5
- int hfreqMax = 0;
6
+ float hfreqMax = 0;
7
for(size_t aMonIter = 0; aMonIter < theMonitors.size(); ++aMonIter) {
8
const StMonitor& aMon = theMonitors[aMonIter];
9
if(aMon.getFreqMax() > hfreqMax) {
10
11
StString& aDescr = myLangMap.changeValueId(STTR_PLUGIN_DESCRIPTION,
12
"(C) {0} Kirill Gavrilov <{1}>\nOfficial site: {2}\n\nThis library is distributed under LGPL3.0");
13
myAbout = aTitle + '\n' + aVerString + " " + StVersionInfo::getSDKVersionString() + "\n \n"
14
- + aDescr.format("2007-2017", "kirill@sview.ru", "www.sview.ru");
15
+ + aDescr.format("2007-2020", "kirill@sview.ru", "www.sview.ru");
16
}
17
18
StOutPageFlip::StOutPageFlip(const StHandle<StResourceManager>& theResMgr,
19
20
// read windowed placement
21
StWindow::hide();
22
if(isMovable()) {
23
- StWindow::setFullScreen(false);
24
+ setFullScreen(false);
25
}
26
}
27
28
29
// Direct3D device will fail to Reset if GL fullscreen device is active
30
// so we switch out main GL window into windowed state temporarily
31
// (we need to wait some time to ensure system perform needed movements)
32
- StWindow::setFullScreen(false);
33
+ setFullScreen(false);
34
StWindow::hide();
35
++myOutD3d.ActivateStep;
36
return;
37
38
if(myOutD3d.ActivateStep == 1) {
39
// at second step switch out main GL window back to fullscreen
40
myOutD3d.ActivateStep = 0;
41
- StWindow::setFullScreen(true);
42
+ setFullScreen(true);
43
StWindow::hide();
44
45
if(myOutD3d.WglDxBuffer.isNull()
46
47
48
// request Quad Buffer
49
StWindow::setAttribute(StWinAttr_GlQuadStereo, params.QuadBuffer->getValue() == QUADBUFFER_HARD_OPENGL);
50
+ if (params.QuadBuffer->getValue() == QUADBUFFER_SOFT) {
51
+ StWindow::setAttribute(StWinAttr_ExclusiveFullScreen, true);
52
+ }
53
if(!StWindow::create()) {
54
return false;
55
}
56
sview-17_04.tar.gz/StOutPageFlip/StOutPageFlip.rc -> sview-20_08.tar.gz/StOutPageFlip/StOutPageFlip.rc
Changed
10
1
2
BEGIN
3
VALUE "FileDescription", "PageFlip Renderer library\000"
4
VALUE "FileVersion", SVIEW_SDK_VER_STRING "\000"
5
- VALUE "LegalCopyright", "\251 2007-2017 Kirill Gavrilov\000"
6
+ VALUE "LegalCopyright", "\251 2007-2020 Kirill Gavrilov and sView developers\000"
7
VALUE "ProductName", "StOutPageFlip\000"
8
VALUE "ProductVersion", SVIEW_SDK_VER_STRING "\000"
9
VALUE "OfficialSite", "www.sview.ru\000"
10
sview-17_04.tar.gz/StOutPageFlip/StOutPageFlipExt.cpp -> sview-20_08.tar.gz/StOutPageFlip/StOutPageFlipExt.cpp
Changed
15
1
2
return true;
3
}
4
5
+void StOutPageFlipExt::setFullScreen(const bool theFullScreen) {
6
+ if(StOutPageFlip::params.QuadBuffer->getValue() == QUADBUFFER_SOFT) {
7
+ setAttribute(StWinAttr_ExclusiveFullScreen, true);
8
+ }
9
+ StOutPageFlip::setFullScreen(theFullScreen);
10
+}
11
+
12
void StOutPageFlipExt::processEvents() {
13
StOutPageFlip::processEvents();
14
if(!StOutPageFlip::params.ToShowExtra->getValue()) {
15
sview-17_04.tar.gz/StOutPageFlip/StOutPageFlipExt.h -> sview-20_08.tar.gz/StOutPageFlip/StOutPageFlipExt.h
Changed
13
1
2
ST_CPPEXPORT virtual void processEvents() ST_ATTR_OVERRIDE;
3
4
/**
5
+ * @param theFullScreen fullscreen state
6
+ */
7
+ ST_CPPEXPORT virtual void setFullScreen(const bool theFullScreen) ST_ATTR_OVERRIDE;
8
+
9
+ /**
10
* Retrieve options list.
11
*/
12
ST_CPPEXPORT virtual void getOptions(StParamsList& theList) const ST_ATTR_OVERRIDE;
13
sview-17_04.tar.gz/StOutPageFlip/StQuadBufferCheck.cpp -> sview-20_08.tar.gz/StOutPageFlip/StQuadBufferCheck.cpp
Changed
15
1
2
return (RegisterClassW(&aClass) != 0);
3
}
4
#elif !defined(__APPLE__) && !defined(ST_HAVE_EGL)
5
+ // exclude modern definitions and system-provided glext.h, should be defined before gl.h inclusion
6
+ #ifndef GL_GLEXT_LEGACY
7
+ #define GL_GLEXT_LEGACY
8
+ #endif
9
+ #ifndef GLX_GLXEXT_LEGACY
10
+ #define GLX_GLXEXT_LEGACY
11
+ #endif
12
#include <GL/glx.h>
13
#endif
14
15
sview-20_08.tar.gz/StOutPageFlip/lang/spanish
Added
2
1
+(directory)
2
sview-20_08.tar.gz/StOutPageFlip/lang/spanish/StOutPageFlip.lng
Added
26
1
2
+# Spanish translation file for StOutPageFlip
3
+--------
4
+1000=Gafas de obturador
5
+1001=Gafas de obturador
6
+1002=Vuzix HMD
7
+1003=Vuzix HMD
8
+1102=Tipo búfer cuádruple
9
+1103=Códigos de control de gafas
10
+1120=OpenGL emulado
11
+1122=OpenGL por hardware
12
+1123=Direct3D (Pantalla completa)
13
+1124=Direct3D (No disponible)
14
+1125=Direct3D AMD (Pantalla completa)
15
+1126=Direct3D AMD (No disponible)
16
+1127=Direct3D NVIDIA (Pantalla completa)
17
+1128=Direct3D NVIDIA (Desactivado)
18
+1130=Sin códigos
19
+1131=Sincronización de línea azul
20
+1132=Sincronización de línea blanca
21
+1134=Apagado/encendido automático de eDimensional
22
+2000=sView - Módulo de salida PageFlip
23
+2001=versión
24
+2002=© {0} Kirill Gavrilov <{1}>\nSitio oficial: {2}
25
+3001=¡El búfer cuádruple OpenGL por hardware no está disponible!\n\nPuedes probar otro tipo de búfer cuádruple\n(Incluido OpenGL emulado en la sección Extra).
26
sview-17_04.tar.gz/StShared/StAVFrame.cpp -> sview-20_08.tar.gz/StShared/StAVFrame.cpp
Changed
18
1
2
#endif
3
}
4
5
+int64_t StAVFrame::getBestEffortTimestamp() const {
6
+#if(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(57, 81, 102)) && !defined(ST_LIBAV_FORK)
7
+ return Frame->best_effort_timestamp;
8
+#elif(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(54, 18, 100)) && !defined(ST_LIBAV_FORK)
9
+ return av_frame_get_best_effort_timestamp(Frame);
10
+#else
11
+ return stAV::NOPTS_VALUE;
12
+#endif
13
+}
14
+
15
void StAVFrame::getImageInfo(const AVCodecContext* theCodecCtx,
16
int& theSizeX,
17
int& theSizeY,
18
sview-17_04.tar.gz/StShared/StAVIOContext.cpp -> sview-20_08.tar.gz/StShared/StAVIOContext.cpp
Changed
10
1
2
StAVIOContext::StAVIOContext()
3
: myAvioCtx(NULL) {
4
const int aBufferSize = 32768;
5
- unsigned char* aBufferIO = (unsigned char* )av_malloc(aBufferSize + FF_INPUT_BUFFER_PADDING_SIZE);
6
+ unsigned char* aBufferIO = (unsigned char* )av_malloc(aBufferSize + AV_INPUT_BUFFER_PADDING_SIZE);
7
myAvioCtx = avio_alloc_context(aBufferIO, aBufferSize, 0, this, readCallback, writeCallback, seekCallback);
8
}
9
10
sview-20_08.tar.gz/StShared/StAVIOJniHttpContext.cpp
Added
417
1
2
+/**
3
+ * Copyright © 2019 Kirill Gavrilov <kirill@sview.ru>
4
+ *
5
+ * Distributed under the Boost Software License, Version 1.0.
6
+ * See accompanying file license-boost.txt or copy at
7
+ * http://www.boost.org/LICENSE_1_0.txt
8
+ */
9
+
10
+#include <StAV/StAVIOJniHttpContext.h>
11
+
12
+#include <StStrings/StLogger.h>
13
+
14
+extern "C" {
15
+ #include <libavutil/error.h>
16
+};
17
+
18
+#if defined(__ANDROID__)
19
+ extern "C" {
20
+ #include <libavcodec/jni.h>
21
+ };
22
+ #include <android/window.h>
23
+ #include <jni.h>
24
+
25
+/**
26
+ * java.net.URLConnection wrapper.
27
+ */
28
+struct StAVIOJniHttpContext::FunctionTable {
29
+
30
+ /**
31
+ * Create java.nio.channels.ReadableByteChannel by opening java.net.URLConnection to specified URL.
32
+ * @param theJEnv [in] attached JavaVM environment
33
+ * @param theUrl [in] URL to open
34
+ * @param theOffset [in] file offset
35
+ * @param theContentLen [out] file length
36
+ * @return local reference to java.nio.channels.ReadableByteChannel
37
+ */
38
+ jobject createNewChannel(StJNIEnv& theJEnv,
39
+ const StString& theUrl,
40
+ int64_t theOffset,
41
+ int64_t& theContentLen) {
42
+ theJEnv->ExceptionClear();
43
+ jobject aJInputStream = createInputStream(theJEnv, theUrl, theOffset, theContentLen);
44
+ if(aJInputStream == NULL) {
45
+ return NULL;
46
+ }
47
+ jobject aJReadChannel = theJEnv->CallStaticObjectMethod(myNioChannels_Class, myNioChannels_newChannel, aJInputStream);
48
+ theJEnv->DeleteLocalRef(aJInputStream);
49
+ return aJReadChannel;
50
+ }
51
+
52
+ /**
53
+ * Read portion of data from opened channel.
54
+ * @sa int java.nio.channels.ReadableByteChannel::read(java.nio.ByteBuffer theBuffer).
55
+ * @param theJEnv [in] attached JavaVM environment
56
+ * @param theChannel [in] opened channel java.nio.channels.ReadableByteChannel
57
+ * @param theBuf [out] buffer to fill
58
+ * @param theBufSize [in] buffer length
59
+ * @return amount of bytes read from channel or -1 on error/EOF; could be also 0 bytes.
60
+ */
61
+ int readChannelIntoBuffer(StJNIEnv& theJEnv,
62
+ jobject theChannel,
63
+ uint8_t* theBuf,
64
+ int theBufSize) {
65
+ theJEnv->ExceptionClear();
66
+ jobject aJBuffer = theJEnv->NewDirectByteBuffer(theBuf, theBufSize);
67
+ if(aJBuffer == NULL) {
68
+ return -1;
69
+ }
70
+
71
+ int aNbReadBytes = theJEnv->CallIntMethod(theChannel, myNioReadableByteChannel_read, aJBuffer);
72
+ theJEnv->DeleteLocalRef(aJBuffer);
73
+ if(theJEnv->ExceptionCheck()) {
74
+ theJEnv->ExceptionClear();
75
+ return -1;
76
+ }
77
+ return aNbReadBytes;
78
+ }
79
+
80
+ /**
81
+ * Load functions.
82
+ */
83
+ bool load(StJNIEnv& theJEnv) {
84
+ if(!myjava_net_URL.load(theJEnv)) {
85
+ return false;
86
+ }
87
+
88
+ jclass aClass = theJEnv->FindClass("java/net/URLConnection");
89
+ if(aClass == NULL) {
90
+ ST_ERROR_LOG("Unable to find java.net.URLConnection class");
91
+ return false;
92
+ }
93
+
94
+ myconnect = theJEnv->GetMethodID(aClass, "connect", "()V");
95
+ mysetRequestProperty = theJEnv->GetMethodID(aClass, "setRequestProperty", "(Ljava/lang/String;Ljava/lang/String;)V");
96
+ mygetInputStream = theJEnv->GetMethodID(aClass, "getInputStream", "()Ljava/io/InputStream;");
97
+ mygetContentLength = theJEnv->GetMethodID(aClass, "getContentLength", "()I");
98
+ mygetContentLengthLong = theJEnv->GetMethodID(aClass, "getContentLengthLong", "()J");
99
+ if(myconnect == NULL || mysetRequestProperty == NULL || mygetInputStream == NULL || mygetContentLength == NULL) {
100
+ ST_ERROR_LOG("Unable to find java.net.URLConnection class methods");
101
+ return false;
102
+ }
103
+
104
+ myNioChannels_Class = theJEnv->FindClass("java/nio/channels/Channels");
105
+ myNioChannels_newChannel = theJEnv->GetStaticMethodID(myNioChannels_Class, "newChannel",
106
+ "(Ljava/io/InputStream;)Ljava/nio/channels/ReadableByteChannel;");
107
+ if(myNioChannels_Class == NULL
108
+ || myNioChannels_newChannel == NULL) {
109
+ ST_ERROR_LOG("Unable to find java.nio.channels.Channels class");
110
+ return false;
111
+ }
112
+ myNioChannels_Class = (jclass )theJEnv->NewGlobalRef(myNioChannels_Class);
113
+
114
+ jclass aNioReadableByteChannel_Class = theJEnv->FindClass("java/nio/channels/ReadableByteChannel");
115
+ myNioReadableByteChannel_read = aNioReadableByteChannel_Class != NULL
116
+ ? theJEnv->GetMethodID(aNioReadableByteChannel_Class, "read", "(Ljava/nio/ByteBuffer;)I")
117
+ : NULL;
118
+ if(myNioReadableByteChannel_read == NULL) {
119
+ ST_ERROR_LOG("Unable to find java.nio.channels.ReadableByteChannel class");
120
+ return false;
121
+ }
122
+ return true;
123
+ }
124
+
125
+ /**
126
+ * Release global references (to Java classes).
127
+ */
128
+ void release(StJNIEnv& theJEnv) {
129
+ myjava_net_URL.release(theJEnv);
130
+ if(myNioChannels_Class != NULL) {
131
+ theJEnv->DeleteGlobalRef(myNioChannels_Class);
132
+ myNioChannels_Class = NULL;
133
+ }
134
+ }
135
+
136
+ private:
137
+
138
+ /**
139
+ * Create java.io.InputStream by opening java.net.URLConnection to specified URL.
140
+ * @param theJEnv [in] attached JavaVM environment
141
+ * @param theUrl [in] URL to open
142
+ * @param theOffset [in] file offset
143
+ * @param theContentLen [out] file length
144
+ * @return local reference to java.io.InputStream
145
+ */
146
+ jobject createInputStream(StJNIEnv& theJEnv,
147
+ const StString& theUrl,
148
+ int64_t theOffset,
149
+ int64_t& theContentLen) {
150
+ jobject aJConnection = myjava_net_URL.openConnection(theJEnv, theUrl);
151
+ if(aJConnection == NULL) {
152
+ return NULL;
153
+ }
154
+
155
+ if(theOffset != 0) {
156
+ StString anOffset = StString("bytes=") + theOffset + "-";
157
+ jstring aJStr_Range = theJEnv->NewStringUTF("Range");
158
+ jstring aJStr_Offset = theJEnv->NewStringUTF(anOffset.toCString());
159
+ theJEnv->CallVoidMethod(aJConnection, mysetRequestProperty, aJStr_Range, aJStr_Offset);
160
+ theJEnv->DeleteLocalRef(aJStr_Range);
161
+ theJEnv->DeleteLocalRef(aJStr_Offset);
162
+ }
163
+ theJEnv->CallVoidMethod(aJConnection, myconnect);
164
+ if(theJEnv->ExceptionCheck()) {
165
+ ST_ERROR_LOG("Unable to open connection java.net.URLConnection '" + theUrl + "'");
166
+ theJEnv->ExceptionClear();
167
+ theJEnv->DeleteLocalRef(aJConnection);
168
+ return NULL;
169
+ }
170
+
171
+ if(mygetContentLengthLong != NULL) {
172
+ theContentLen = theJEnv->CallLongMethod(aJConnection, mygetContentLengthLong);
173
+ } else {
174
+ theContentLen = theJEnv->CallIntMethod(aJConnection, mygetContentLength);
175
+ }
176
+
177
+ jobject aJInputStream = theJEnv->CallObjectMethod(aJConnection, mygetInputStream);
178
+ theJEnv->DeleteLocalRef(aJConnection);
179
+ if(theJEnv->ExceptionCheck()) {
180
+ theJEnv->ExceptionClear();
181
+ if(aJInputStream != NULL) {
182
+ theJEnv->DeleteLocalRef(aJInputStream);
183
+ aJInputStream = NULL;
184
+ }
185
+ }
186
+ if(aJInputStream == NULL) {
187
+ ST_ERROR_LOG("Unable to create java.io.InputStream");
188
+ }
189
+ return aJInputStream;
190
+ }
191
+
192
+ // java.net.URL wrapper.
193
+ struct st_java_net_URL {
194
+
195
+ /**
196
+ * Load java.net.URL class and its methods.
197
+ */
198
+ bool load(StJNIEnv& theJEnv) {
199
+ myClass = theJEnv->FindClass("java/net/URL");
200
+ if(myClass == NULL) {
201
+ ST_ERROR_LOG("Unable to find java.net.URL class");
202
+ return false;
203
+ }
204
+
205
+ myClass = (jclass )theJEnv->NewGlobalRef(myClass);
206
+ myInit = theJEnv->GetMethodID(myClass, "<init>", "(Ljava/lang/String;)V");
207
+ myopenConnection = theJEnv->GetMethodID(myClass, "openConnection", "()Ljava/net/URLConnection;");
208
+ if(myInit == NULL || myopenConnection == NULL) {
209
+ ST_ERROR_LOG("Unable to find java.net.URL class methods");
210
+ release(theJEnv);
211
+ return false;
212
+ }
213
+ return true;
214
+ }
215
+
216
+ /**
217
+ * Release global references (to Java class).
218
+ */
219
+ void release(StJNIEnv& theJEnv) {
220
+ if(myClass != NULL) {
221
+ theJEnv->DeleteGlobalRef(myClass);
222
+ myClass = NULL;
223
+ }
224
+ }
225
+
226
+ /**
227
+ * Create java.net.URLConnection opening specified URL.
228
+ * Return local reference or NULL on failure.
229
+ */
230
+ jobject openConnection(StJNIEnv& theJEnv, const StString& theUrl) {
231
+ jobject aJNetUrl = create(theJEnv, theUrl);
232
+ if(aJNetUrl == NULL) {
233
+ ST_ERROR_LOG("Unable to create java.net.URL");
234
+ return NULL;
235
+ }
236
+
237
+ jobject aJNetUrlCon = theJEnv->CallObjectMethod(aJNetUrl, myopenConnection);
238
+ theJEnv->DeleteLocalRef(aJNetUrl);
239
+ if(theJEnv->ExceptionCheck()) {
240
+ theJEnv->ExceptionClear();
241
+ if(aJNetUrlCon != NULL) {
242
+ theJEnv->DeleteLocalRef(aJNetUrlCon);
243
+ aJNetUrlCon = NULL;
244
+ }
245
+ }
246
+ if(aJNetUrlCon == NULL) {
247
+ ST_ERROR_LOG("Unable to create java.net.URLConnection");
248
+ return NULL;
249
+ }
250
+ return aJNetUrlCon;
251
+ }
252
+
253
+ private:
254
+
255
+ /**
256
+ * Create java.net.URL class instance with specified URL; returns local reference.
257
+ */
258
+ jobject create(StJNIEnv& theJEnv, const StString& theUrl) {
259
+ jstring aJStr_Url = theJEnv->NewStringUTF(theUrl.toCString());
260
+ jobject aNetURL = theJEnv->NewObject(myClass, myInit, aJStr_Url);
261
+ theJEnv->DeleteLocalRef(aJStr_Url);
262
+ return aNetURL;
263
+ }
264
+
265
+ private:
266
+
267
+ jclass myClass = NULL;
268
+ jmethodID myInit = NULL;
269
+ jmethodID myopenConnection = NULL;
270
+
271
+ } myjava_net_URL;
272
+
273
+ // java.net.URLConnection
274
+ jmethodID myconnect = NULL;
275
+ jmethodID mysetRequestProperty = NULL;
276
+ jmethodID mygetInputStream = NULL;
277
+ jmethodID mygetContentLength = NULL;
278
+ jmethodID mygetContentLengthLong = NULL;
279
+
280
+ // java.nio.channels.Channels
281
+ jclass myNioChannels_Class = NULL;
282
+ jmethodID myNioChannels_newChannel = NULL;
283
+
284
+ //java.nio.channels.ReadableByteChannel
285
+ //myNioReadableByteChannel_Class = NULL
286
+ jmethodID myNioReadableByteChannel_read = NULL;
287
+
288
+};
289
+#endif
290
+
291
+StAVIOJniHttpContext::StAVIOJniHttpContext()
292
+: myFunctions(NULL),
293
+#if defined(__ANDROID__)
294
+ myJEnv((JavaVM* )av_jni_get_java_vm(NULL)),
295
+#else
296
+ myJEnv(NULL),
297
+#endif
298
+ myReadChannel(NULL),
299
+ myContentLen(0),
300
+ myPosition(0) {
301
+#if defined(__ANDROID__)
302
+ if(!myJEnv.isNull()) {
303
+ myFunctions = new FunctionTable();
304
+ if(!myFunctions->load(myJEnv)) {
305
+ myFunctions->release(myJEnv);
306
+ myJEnv.detach();
307
+ }
308
+ }
309
+#endif
310
+}
311
+
312
+StAVIOJniHttpContext::~StAVIOJniHttpContext() {
313
+ close();
314
+ if(myFunctions != NULL) {
315
+ #if defined(__ANDROID__)
316
+ myFunctions->release(myJEnv);
317
+ delete myFunctions;
318
+ #endif
319
+ }
320
+}
321
+
322
+void StAVIOJniHttpContext::close() {
323
+ if(myReadChannel != NULL) {
324
+ #if defined(__ANDROID__)
325
+ myJEnv->DeleteGlobalRef((jobject )myReadChannel);
326
+ #endif
327
+ myReadChannel = NULL;
328
+ }
329
+}
330
+
331
+bool StAVIOJniHttpContext::reopenReadChannel(int64_t theOffset) {
332
+ if(myJEnv.isNull()) {
333
+ return false;
334
+ }
335
+
336
+#if defined(__ANDROID__)
337
+ if(myReadChannel != NULL) {
338
+ myJEnv->DeleteGlobalRef((jobject )myReadChannel);
339
+ myReadChannel = NULL;
340
+ }
341
+
342
+ /**
343
+ * java.net.URL anUrl = new java.net.URL(aPath);
344
+ * java.net.URLConnection anUrlConnection = anUrl.openConnection();
345
+ * anUrlConnection.setRequestProperty ("Range", "bytes="+offset+"-");
346
+ * anUrlConnection.connect();
347
+ * java.io.InputStream anInputStream = anUrlConnection.getInputStream();
348
+ * java.nio.channels.ReadableByteChannel aReadableByteChannel = java.nio.channels.Channels.newChannel(anInputStream);
349
+ */
350
+ jobject aJReadChannel = myFunctions->createNewChannel(myJEnv, myUrl, theOffset, myContentLen);
351
+ if(aJReadChannel == NULL) {
352
+ myReadChannel = NULL;
353
+ return false;
354
+ }
355
+ myReadChannel = myJEnv->NewGlobalRef(aJReadChannel);
356
+ myPosition = theOffset;
357
+ return true;
358
+#else
359
+ (void )theOffset;
360
+ return false;
361
+#endif
362
+}
363
+
364
+bool StAVIOJniHttpContext::open(const StString& theUrl) {
365
+ close();
366
+ myUrl = theUrl;
367
+ return reopenReadChannel(0);
368
+}
369
+
370
+int StAVIOJniHttpContext::read(uint8_t* theBuf,
371
+ int theBufSize) {
372
+ if(myReadChannel == NULL
373
+ || theBuf == NULL
374
+ || theBufSize <= 0) {
375
+ return -1;
376
+ }
377
+
378
+#if defined(__ANDROID__)
379
+ int aNbRead = myFunctions->readChannelIntoBuffer(myJEnv, (jobject )myReadChannel, theBuf, theBufSize);
380
+ if(aNbRead == -1) {
381
+ return AVERROR_EOF;
382
+ }
383
+ return aNbRead;
384
+#else
385
+ return -1;
386
+#endif
387
+}
388
+
389
+int64_t StAVIOJniHttpContext::seek(int64_t theOffset,
390
+ int theWhence) {
391
+ if(myReadChannel == NULL) {
392
+ return -1;
393
+ }
394
+
395
+ switch(theWhence) {
396
+ case AVSEEK_SIZE: {
397
+ return myContentLen != 0 ? myContentLen : -1;
398
+ }
399
+ case SEEK_SET: {
400
+ reopenReadChannel(theOffset);
401
+ return myPosition;
402
+ }
403
+ case SEEK_CUR: {
404
+ reopenReadChannel(myPosition + theOffset);
405
+ return myPosition;
406
+ }
407
+ case SEEK_END: {
408
+ if(myContentLen <= 0) {
409
+ return -1;
410
+ }
411
+ reopenReadChannel(myContentLen + theOffset);
412
+ return myPosition;
413
+ }
414
+ }
415
+ return -1;
416
+}
417
sview-17_04.tar.gz/StShared/StAVImage.cpp -> sview-20_08.tar.gz/StShared/StAVImage.cpp
Changed
239
1
2
/**
3
- * Copyright © 2011-2015 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2011-2020 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* Distributed under the Boost Software License, Version 1.0.
7
* See accompanying file license-boost.txt or copy at
8
9
}
10
}
11
switch(theImage.getColorModel()) {
12
- case StImage::ImgColor_YUV: {
13
+ case StImage::ImgColor_YUV:
14
+ case StImage::ImgColor_YUVA: {
15
size_t aDelimX = (theImage.getPlane(1).getSizeX() > 0) ? (aPlane0.getSizeX() / theImage.getPlane(1).getSizeX()) : 1;
16
size_t aDelimY = (theImage.getPlane(1).getSizeY() > 0) ? (aPlane0.getSizeY() / theImage.getPlane(1).getSizeY()) : 1;
17
if(theImage.getPlane(1).getFormat() == StImagePlane::ImgUV) {
18
19
}
20
} else if(aDelimX == 1 && aDelimY == 2) {
21
return theImage.getColorScale() == StImage::ImgScale_Mpeg
22
- ? stAV::PIX_FMT::YUVJ440P : stAV::PIX_FMT::YUV440P;
23
+ ? stAV::PIX_FMT::YUV440P : stAV::PIX_FMT::YUVJ440P;
24
} else if(aDelimX == 4 && aDelimY == 1) {
25
return stAV::PIX_FMT::YUV411P;
26
} else if(aDelimX == 4 && aDelimY == 4) {
27
28
}
29
}
30
31
+static const int THE_SWSCALE_FLAGS_FAST = SWS_BICUBIC;
32
+static const int THE_SWSCALE_FLAGS_QUALITY = SWS_LANCZOS | SWS_ACCURATE_RND | SWS_FULL_CHR_H_INT;
33
+
34
/**
35
* Convert image from one format to another using swscale.
36
* Image buffers should be already initialized!
37
*/
38
static bool convert(const StImage& theImageFrom, AVPixelFormat theFormatFrom,
39
- StImage& theImageTo, AVPixelFormat theFormatTo) {
40
+ StImage& theImageTo, AVPixelFormat theFormatTo,
41
+ int theSwsFlags) {
42
ST_DEBUG_LOG("StAVImage, convert from " + stAV::PIX_FMT::getString(theFormatFrom) + " " + theImageFrom.getSizeX() + "x" + theImageFrom.getSizeY()
43
+ " to " + stAV::PIX_FMT::getString(theFormatTo) + " " + theImageTo.getSizeX() + "x" + theImageTo.getSizeY());
44
if(theFormatFrom == stAV::PIX_FMT::NONE
45
46
47
SwsContext* aCtxToRgb = sws_getContext((int )theImageFrom.getSizeX(), (int )theImageFrom.getSizeY(), theFormatFrom, // source
48
(int )theImageTo.getSizeX(), (int )theImageTo.getSizeY(), theFormatTo, // destination
49
- SWS_BICUBIC, NULL, NULL, NULL);
50
+ theSwsFlags, NULL, NULL, NULL);
51
if(aCtxToRgb == NULL) {
52
return false;
53
}
54
55
return true;
56
}
57
58
+/**
59
+ * Return AV pixel format for an image plane.
60
+ */
61
+static int getAVPixelFormatForPlane(const StImagePlane& theImage) {
62
+ switch(theImage.getFormat()) {
63
+ case StImagePlane::ImgRGB: return stAV::PIX_FMT::RGB24;
64
+ case StImagePlane::ImgBGR: return stAV::PIX_FMT::BGR24;
65
+ case StImagePlane::ImgRGBA: return stAV::PIX_FMT::RGBA32;
66
+ case StImagePlane::ImgBGRA: return stAV::PIX_FMT::BGRA32;
67
+ case StImagePlane::ImgGray: return stAV::PIX_FMT::GRAY8;
68
+ case StImagePlane::ImgGray16: return stAV::PIX_FMT::GRAY16;
69
+ default: return stAV::PIX_FMT::NONE;
70
+ }
71
+}
72
+
73
+bool StAVImage::resizePlane(const StImagePlane& theImageFrom,
74
+ StImagePlane& theImageTo) {
75
+ if(theImageFrom.isNull()
76
+ || theImageFrom.getSizeX() < 1
77
+ || theImageFrom.getSizeY() < 1
78
+ || theImageTo.isNull()
79
+ || theImageTo.getSizeX() < 1
80
+ || theImageTo.getSizeY() < 1) {
81
+ return false;
82
+ }
83
+
84
+ StAVImage::init();
85
+ const AVPixelFormat aFormatFrom = (AVPixelFormat )getAVPixelFormatForPlane(theImageFrom);
86
+ const AVPixelFormat aFormatTo = (AVPixelFormat )getAVPixelFormatForPlane(theImageTo);
87
+ if(aFormatFrom == stAV::PIX_FMT::NONE
88
+ || aFormatTo == stAV::PIX_FMT::NONE) {
89
+ return false;
90
+ }
91
+
92
+ SwsContext* aCtxToRgb = sws_getContext((int )theImageFrom.getSizeX(), (int )theImageFrom.getSizeY(), aFormatFrom,
93
+ (int )theImageTo.getSizeX(), (int )theImageTo.getSizeY(), aFormatTo,
94
+ THE_SWSCALE_FLAGS_FAST, NULL, NULL, NULL);
95
+ if(aCtxToRgb == NULL) {
96
+ return false;
97
+ }
98
+
99
+ uint8_t* aSrcData[4] = { (uint8_t* )theImageFrom.getData(), NULL, NULL, NULL };
100
+ int aSrcLinesize[4] = { (int )theImageFrom.getSizeRowBytes(), 0, 0, 0 };
101
+ uint8_t* aDstData[4] = { (uint8_t* )theImageTo.getData(), NULL, NULL, NULL };
102
+ int aDstLinesize[4] = { (int )theImageTo.getSizeRowBytes(), 0, 0, 0 };
103
+ sws_scale(aCtxToRgb,
104
+ aSrcData, aSrcLinesize,
105
+ 0, (int )theImageFrom.getSizeY(),
106
+ aDstData, aDstLinesize);
107
+ sws_freeContext(aCtxToRgb);
108
+ return true;
109
+}
110
+
111
bool StAVImage::resize(const StImage& theImageFrom,
112
StImage& theImageTo) {
113
if(theImageFrom.isNull()
114
115
return aFormatFrom != stAV::PIX_FMT::NONE
116
&& aFormatTo != stAV::PIX_FMT::NONE
117
&& convert(theImageFrom, aFormatFrom,
118
- theImageTo, aFormatTo);
119
+ theImageTo, aFormatTo,
120
+ THE_SWSCALE_FLAGS_FAST);
121
}
122
123
void StAVImage::close() {
124
125
myCodec = avcodec_find_decoder_by_name("webp");
126
break;
127
}
128
+ case ST_TYPE_DDS: {
129
+ myCodec = avcodec_find_decoder_by_name("dds");
130
+ break;
131
+ }
132
default: {
133
break;
134
}
135
136
#endif
137
if(avErrCode != 0
138
|| myFormatCtx->nb_streams < 1
139
- || myFormatCtx->streams[0]->codec->codec_id == 0) {
140
+ || stAV::getCodecId(myFormatCtx->streams[0]) == AV_CODEC_ID_NONE) {
141
if(myFormatCtx != NULL) {
142
#if(LIBAVFORMAT_VERSION_INT >= AV_VERSION_INT(53, 17, 0))
143
avformat_close_input(&myFormatCtx);
144
145
}
146
147
// find the decoder for the video stream
148
- myCodecCtx = myFormatCtx->streams[0]->codec;
149
+ myCodecCtx = stAV::getCodecCtx(myFormatCtx->streams[0]);
150
if(theImageType == ST_TYPE_NONE) {
151
myCodec = avcodec_find_decoder(myCodecCtx->codec_id);
152
}
153
154
155
// decode one frame
156
int isFrameFinished = 0;
157
-#if(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(52, 23, 0))
158
+#if(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(57, 106, 102))
159
+ if(avcodec_send_packet(myCodecCtx, anAvPkt.getAVpkt()) == 0
160
+ && avcodec_receive_frame(myCodecCtx, myFrame.Frame) == 0) {
161
+ isFrameFinished = 1;
162
+ }
163
+#elif(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(52, 23, 0))
164
avcodec_decode_video2(myCodecCtx, myFrame.Frame, &isFrameFinished, anAvPkt.getAVpkt());
165
#else
166
avcodec_decode_video(myCodecCtx, myFrame.Frame, &isFrameFinished,
167
168
aDimsYUV.isFullScale = true;
169
}
170
#endif
171
- setColorModel(StImage::ImgColor_YUV);
172
+ setColorModel(aDimsYUV.hasAlpha ? StImage::ImgColor_YUVA : StImage::ImgColor_YUV);
173
setColorScale(aDimsYUV.isFullScale ? StImage::ImgScale_Full : StImage::ImgScale_Mpeg);
174
StImagePlane::ImgFormat aPlaneFrmt = StImagePlane::ImgGray;
175
if(aDimsYUV.bitsPerComp == 9) {
176
177
size_t(aDimsYUV.widthU), size_t(aDimsYUV.heightU), myFrame.getLineSize(1));
178
changePlane(2).initWrapper(aPlaneFrmt, myFrame.getPlane(2),
179
size_t(aDimsYUV.widthV), size_t(aDimsYUV.heightV), myFrame.getLineSize(2));
180
+ if(aDimsYUV.hasAlpha) {
181
+ changePlane(3).initWrapper(aPlaneFrmt, myFrame.getPlane(3),
182
+ size_t(aDimsYUV.widthY), size_t(aDimsYUV.heightY), myFrame.getLineSize(3));
183
+ }
184
} else {
185
///ST_DEBUG_LOG("StAVImage, perform conversion from Pixel format '" + avcodec_get_pix_fmt_name(myCodecCtx->pix_fmt) + "' to RGB");
186
// initialize software scaler/converter
187
188
anImage.changePlane().initTrash(StImagePlane::ImgRGB, getSizeX(), getSizeY(), getAligned(getSizeX() * 3));
189
AVPixelFormat aPFrmtTarget = stAV::PIX_FMT::RGB24;
190
if(!convert(*this, aPFormatAV,
191
- anImage, aPFrmtTarget)) {
192
+ anImage, aPFrmtTarget,
193
+ THE_SWSCALE_FLAGS_QUALITY)) {
194
setState("SWScale library, failed to create SWScaler context");
195
close();
196
return false;
197
198
anImage.changePlane(2).initTrash(StImagePlane::ImgGray, getSizeX(), getSizeY(), getAligned(getSizeX()));
199
stMemSet(anImage.changePlane(2).changeData(), '\0', anImage.getPlane(2).getSizeBytes());
200
if(!convert(*this, aPFormatAV,
201
- anImage, aPFrmtTarget)) {
202
+ anImage, aPFrmtTarget,
203
+ THE_SWSCALE_FLAGS_QUALITY)) {
204
setState("SWScale library, failed to create SWScaler context");
205
close();
206
return false;
207
208
return false;
209
}
210
211
+ // encode the image
212
+ StAVPacket aPacket;
213
+#if(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(57, 106, 102))
214
+ int anEncSize = 0;
215
+ if(avcodec_send_frame(myCodecCtx, myFrame.Frame) == 0
216
+ && avcodec_receive_packet(myCodecCtx, aPacket.getAVpkt()) == 0
217
+ && aPacket.getAVpkt()->data != NULL) {
218
+ anEncSize = aPacket.getSize();
219
+ aRawFile.wrapBuffer(aPacket.getAVpkt()->data, anEncSize);
220
+ }
221
+#else
222
// allocate the buffer, large enough (stupid formula copied from ffmpeg.c)
223
int aBuffSize = int(getSizeX() * getSizeY() * 10);
224
aRawFile.initBuffer(aBuffSize);
225
-
226
- // encode the image
227
- StAVPacket aPacket;
228
aPacket.getAVpkt()->data = (uint8_t* )aRawFile.changeBuffer();
229
aPacket.getAVpkt()->size = aBuffSize;
230
#if(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(54, 2, 100))
231
232
#else
233
int anEncSize = avcodec_encode_video(myCodecCtx, aPacket.changeData(), aPacket.getSize(), myFrame.Frame);
234
#endif
235
+#endif
236
if(anEncSize <= 0) {
237
setState("AVCodec library, fail to encode the image");
238
close();
239
sview-17_04.tar.gz/StShared/StAVPacket.cpp -> sview-20_08.tar.gz/StShared/StAVPacket.cpp
Changed
61
1
2
myIsOwn(false) {
3
avInitPacket();
4
if(myType == DATA_PACKET) {
5
+ #if(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(57, 106, 102))
6
+ av_packet_ref(&myPacket, &theCopy.myPacket); // copy by reference
7
+ #else
8
setAVpkt(theCopy.myPacket);
9
+ #endif
10
}
11
}
12
13
14
void StAVPacket::free() {
15
if(myIsOwn) {
16
avDestructPacket(&myPacket);
17
+ avInitPacket();
18
} else {
19
- #if(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(55, 0, 0))
20
+ #if(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(57, 12, 100))
21
+ av_packet_unref(&myPacket);
22
+ #elif(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(55, 0, 0))
23
av_free_packet(&myPacket);
24
+ avInitPacket();
25
#else
26
if(myPacket.destruct != NULL) {
27
myPacket.destruct(&myPacket);
28
myPacket.destruct = NULL;
29
}
30
+ avInitPacket();
31
#endif
32
}
33
- avInitPacket();
34
myIsOwn = false;
35
}
36
37
38
#endif
39
40
// now copy data with special padding space
41
- myPacket.data = stMemAllocAligned<uint8_t*>((theCopy.size + FF_INPUT_BUFFER_PADDING_SIZE), 16); // data must be aligned to 16 bytes for SSE!
42
+ myPacket.data = stMemAllocAligned<uint8_t*>((theCopy.size + AV_INPUT_BUFFER_PADDING_SIZE), 16); // data must be aligned to 16 bytes for SSE!
43
stMemCpy (myPacket.data, theCopy.data, theCopy.size);
44
- stMemZero(myPacket.data + (ptrdiff_t )theCopy.size, FF_INPUT_BUFFER_PADDING_SIZE);
45
+ stMemZero(myPacket.data + (ptrdiff_t )theCopy.size, AV_INPUT_BUFFER_PADDING_SIZE);
46
47
#if(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(52, 118, 0))
48
if(myPacket.side_data_elems > 0) {
49
50
for(int anIter = 0; anIter < theCopy.side_data_elems; ++anIter) {
51
aSize = theCopy.side_data[anIter].size;
52
myPacket.side_data[anIter] = theCopy.side_data[anIter];
53
- myPacket.side_data[anIter].data = stMemAllocAligned<uint8_t*>(aSize + FF_INPUT_BUFFER_PADDING_SIZE, 16);
54
+ myPacket.side_data[anIter].data = stMemAllocAligned<uint8_t*>(aSize + AV_INPUT_BUFFER_PADDING_SIZE, 16);
55
stMemCpy (myPacket.side_data[anIter].data, theCopy.side_data[anIter].data, aSize);
56
- stMemZero(myPacket.side_data[anIter].data + (ptrdiff_t )aSize, FF_INPUT_BUFFER_PADDING_SIZE);
57
+ stMemZero(myPacket.side_data[anIter].data + (ptrdiff_t )aSize, AV_INPUT_BUFFER_PADDING_SIZE);
58
}
59
}
60
#endif
61
sview-17_04.tar.gz/StShared/StAVVideoMuxer.cpp -> sview-20_08.tar.gz/StShared/StAVVideoMuxer.cpp
Changed
125
1
2
3
bool StAVVideoMuxer::addStream(AVFormatContext* theContext,
4
AVStream* theStream) {
5
+ AVCodecContext* aCodecCtxSrc = stAV::getCodecCtx(theStream);
6
#if(LIBAVFORMAT_VERSION_INT >= AV_VERSION_INT(57, 0, 0))
7
- AVStream* aStreamOut = avformat_new_stream(theContext, theStream->codec->codec);
8
+ AVStream* aStreamOut = avformat_new_stream(theContext, aCodecCtxSrc->codec);
9
#else
10
- AVStream* aStreamOut = avformat_new_stream(theContext, (AVCodec* )theStream->codec->codec);
11
+ AVStream* aStreamOut = avformat_new_stream(theContext, (AVCodec* )aCodecCtxSrc->codec);
12
#endif
13
if(aStreamOut == NULL) {
14
signals.onError(StString("Failed allocating output stream."));
15
return false;
16
}
17
- if(avcodec_copy_context(aStreamOut->codec, theStream->codec) < 0) {
18
+ AVCodecContext* aCodecCtxNew = stAV::getCodecCtx(aStreamOut);
19
+ if(avcodec_copy_context(aCodecCtxNew, aCodecCtxSrc) < 0) {
20
signals.onError(StString("Failed to copy context from input to output stream codec context."));
21
return false;
22
}
23
24
//#if(LIBAVFORMAT_VERSION_INT >= AV_VERSION_INT(54, 2, 100))
25
// myIsAttachedPic = (theStream->disposition & AV_DISPOSITION_ATTACHED_PIC) != 0;
26
//#endif
27
- if(theStream->codec->codec_type == AVMEDIA_TYPE_VIDEO) {
28
- aStreamOut->sample_aspect_ratio = theStream->sample_aspect_ratio;
29
- aStreamOut->codec->sample_aspect_ratio = aStreamOut->sample_aspect_ratio;
30
+ if(aCodecCtxSrc->codec_type == AVMEDIA_TYPE_VIDEO) {
31
+ aStreamOut->sample_aspect_ratio = theStream->sample_aspect_ratio;
32
+ aCodecCtxNew->sample_aspect_ratio = aStreamOut->sample_aspect_ratio;
33
}
34
35
if(theContext->oformat->flags & AVFMT_GLOBALHEADER) {
36
- aStreamOut->codec->flags |= CODEC_FLAG_GLOBAL_HEADER;
37
+ aCodecCtxNew->flags |= AV_CODEC_FLAG_GLOBAL_HEADER;
38
}
39
return true;
40
}
41
42
for(unsigned int aStreamId = 0; aStreamId < aCtxSrc.Context->nb_streams; ++aStreamId) {
43
aCtxSrc.Streams.add((unsigned int )-1);
44
AVStream* aStreamSrc = aCtxSrc.Context->streams[aStreamId];
45
- if(aStreamSrc->codec->codec_type == AVMEDIA_TYPE_VIDEO) {
46
+ if(stAV::getCodecType(aStreamSrc) == AVMEDIA_TYPE_VIDEO) {
47
if(addStream(aCtxOut.Context, aStreamSrc)) {
48
aCtxSrc.Streams[aStreamId] = aStreamCount++;
49
}
50
51
StRemuxContext& aCtxSrc = aSrcCtxList[aCtxId];
52
for(unsigned int aStreamId = 0; aStreamId < aCtxSrc.Context->nb_streams; ++aStreamId) {
53
AVStream* aStreamSrc = aCtxSrc.Context->streams[aStreamId];
54
- if(aStreamSrc->codec->codec_type == AVMEDIA_TYPE_AUDIO
55
+ if(stAV::getCodecType(aStreamSrc) == AVMEDIA_TYPE_AUDIO
56
&& addStream(aCtxOut.Context, aStreamSrc)) {
57
aCtxSrc.Streams[aStreamId] = aStreamCount++;
58
}
59
60
StRemuxContext& aCtxSrc = aSrcCtxList[aCtxId];
61
for(unsigned int aStreamId = 0; aStreamId < aCtxSrc.Context->nb_streams; ++aStreamId) {
62
AVStream* aStreamSrc = aCtxSrc.Context->streams[aStreamId];
63
- if(aStreamSrc->codec->codec_type != AVMEDIA_TYPE_VIDEO
64
- && aStreamSrc->codec->codec_type != AVMEDIA_TYPE_AUDIO
65
+ if(stAV::getCodecType(aStreamSrc) != AVMEDIA_TYPE_VIDEO
66
+ && stAV::getCodecType(aStreamSrc) != AVMEDIA_TYPE_AUDIO
67
&& addStream(aCtxOut.Context, aStreamSrc)) {
68
aCtxSrc.Streams[aStreamId] = aStreamCount++;
69
}
70
71
return false;
72
}
73
74
- AVPacket aPacket;
75
+ StAVPacket aPacket;
76
for(;;) {
77
size_t aNbEmpty = 0;
78
for(size_t aCtxId = 0; aCtxId < aSrcCtxList.size(); ++aCtxId) {
79
80
continue;
81
}
82
83
- if(av_read_frame(aCtxSrc.Context, &aPacket) < 0) {
84
+ if(av_read_frame(aCtxSrc.Context, aPacket.getAVpkt()) < 0) {
85
aCtxSrc.State = false;
86
++aNbEmpty;
87
continue;
88
}
89
90
- unsigned int aStreamOutIndex = aCtxSrc.Streams[aPacket.stream_index];
91
+ unsigned int aStreamOutIndex = aCtxSrc.Streams[aPacket.getStreamId()];
92
if(aStreamOutIndex == (unsigned int )-1) {
93
continue;
94
}
95
96
- AVStream* aStreamIn = aCtxSrc.Context->streams[aPacket.stream_index];
97
+ AVStream* aStreamIn = aCtxSrc.Context->streams[aPacket.getStreamId()];
98
AVStream* aStreamOut = aCtxOut.Context->streams[aStreamOutIndex];
99
100
#ifdef ST_LIBAV_FORK
101
102
#else
103
const AVRounding aRoundParams = AVRounding(AV_ROUND_NEAR_INF | AV_ROUND_PASS_MINMAX);
104
#endif
105
- aPacket.pts = av_rescale_q_rnd(aPacket.pts, aStreamIn->time_base, aStreamOut->time_base, aRoundParams);
106
- aPacket.dts = av_rescale_q_rnd(aPacket.dts, aStreamIn->time_base, aStreamOut->time_base, aRoundParams);
107
- aPacket.duration = static_cast<int >(av_rescale_q(aPacket.duration, aStreamIn->time_base, aStreamOut->time_base));
108
- aPacket.pos = -1;
109
+ aPacket.getAVpkt()->pts = av_rescale_q_rnd(aPacket.getPts(), aStreamIn->time_base, aStreamOut->time_base, aRoundParams);
110
+ aPacket.getAVpkt()->dts = av_rescale_q_rnd(aPacket.getDts(), aStreamIn->time_base, aStreamOut->time_base, aRoundParams);
111
+ aPacket.getAVpkt()->duration = static_cast<int >(av_rescale_q(aPacket.getDuration(), aStreamIn->time_base, aStreamOut->time_base));
112
+ aPacket.getAVpkt()->pos = -1;
113
114
- aState = av_interleaved_write_frame(aCtxOut.Context, &aPacket);
115
+ aState = av_interleaved_write_frame(aCtxOut.Context, aPacket.getAVpkt());
116
if(aState < 0) {
117
signals.onError(StString("Error muxing packet (") + stAV::getAVErrorDescription(aState) + ").");
118
return false;
119
}
120
- av_free_packet(&aPacket);
121
+ aPacket.free();
122
}
123
if(aNbEmpty == aSrcCtxList.size()) {
124
break;
125
sview-17_04.tar.gz/StShared/StAction.cpp -> sview-20_08.tar.gz/StShared/StAction.cpp
Changed
25
1
2
/**
3
- * Copyright © 2013 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2013-2017 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* Distributed under the Boost Software License, Version 1.0.
7
* See accompanying file license-boost.txt or copy at
8
9
10
StAction::StAction(const StCString& theName)
11
: myName(theName),
12
- myHotKey1(0),
13
- myHotKey2(0),
14
- myDefaultHotKey1(0),
15
- myDefaultHotKey2(0),
16
myToHoldKey(false) {
17
- //
18
+ myHotKeys[0] = 0;
19
+ myHotKeys[1] = 0;
20
+ myHotKeysDef[0] = 0;
21
+ myHotKeysDef[1] = 0;
22
}
23
24
StAction::~StAction() {}
25
sview-17_04.tar.gz/StShared/StCocoaCoords.mm -> sview-20_08.tar.gz/StShared/StCocoaCoords.mm
Changed
11
1
2
CGDirectDisplayID aDispId = [aNumber unsignedIntValue];
3
CGRect aRect = CGDisplayBounds(aDispId);
4
myScreenBottom = aRect.origin.y + aRect.size.height;
5
+ST_DISABLE_DEPRECATION_WARNINGS
6
myScale = [aScreen userSpaceScaleFactor];
7
+ST_ENABLE_DEPRECATION_WARNINGS
8
myUnScale = 1.0 / myScale;
9
return true;
10
}
11
sview-17_04.tar.gz/StShared/StConfigImpl.cpp -> sview-20_08.tar.gz/StShared/StConfigImpl.cpp
Changed
19
1
2
} catch(ParseException& ex) {
3
ST_DEBUG_LOG("StSettings, error on line " + ex.getLine() + ": " + ex.getError());
4
return false;
5
- } catch(SettingNotFoundException nfex) {
6
+ } catch(SettingNotFoundException& nfex) {
7
ST_DEBUG_LOG("StSettings, setting not found: " + nfex.getPath());
8
return false;
9
} catch(ConfigException& cex) {
10
11
} catch(ParseException& ex) {
12
ST_DEBUG_LOG("StSettings, error on line " + ex.getLine() + ": " + ex.getError());
13
return false;
14
- } catch(SettingNotFoundException nfex) {
15
+ } catch(SettingNotFoundException& nfex) {
16
ST_DEBUG_LOG("StSettings, setting not found: " + nfex.getPath());
17
return false;
18
} catch(ConfigException& cex) {
19
sview-17_04.tar.gz/StShared/StDevILImage.cpp -> sview-20_08.tar.gz/StShared/StDevILImage.cpp
Changed
17
1
2
#define IL_PNG 0x042A
3
#define IL_PSD 0x0439
4
#define IL_HDR 0x043F
5
+#define IL_DDS 0x0437
6
7
// Matches OpenGL's right now.
8
#define IL_RGB 0x1907
9
10
case StImageFile::ST_TYPE_JPS: return IL_JPG;
11
case StImageFile::ST_TYPE_PSD: return IL_PSD;
12
case StImageFile::ST_TYPE_HDR: return IL_HDR;
13
+ case StImageFile::ST_TYPE_DDS: return IL_DDS;
14
case StImageFile::ST_TYPE_NONE:
15
default:
16
return IL_TYPE_UNKNOWN;
17
sview-17_04.tar.gz/StShared/StExifDir.cpp -> sview-20_08.tar.gz/StShared/StExifDir.cpp
Changed
25
1
2
}
3
}
4
} else {
5
- ST_DEBUG_LOG("StExifDir, found unsupported (" + CameraMaker + ") maker notes");
6
+ if(anEntry.Format == StExifEntry::FMT_STRING) {
7
+ StString aMakerNoteName((char *)anEntry.ValuePtr);
8
+ ST_DEBUG_LOG("StExifDir, found unsupported (" + aMakerNoteName + ") maker notes");
9
+ } else {
10
+ ST_DEBUG_LOG("StExifDir, found unsupported (" + CameraMaker + ": " + CameraModel + ") maker notes");
11
+ }
12
}
13
break;
14
}
15
16
if(aDir->Type == theQuery.Type) {
17
for(size_t anEntryId = 0; anEntryId < aDir->Entries.size(); ++anEntryId) {
18
const StExifEntry& anEntry = aDir->Entries[anEntryId];
19
- if(anEntry.Tag == theQuery.Entry.Tag) {
20
+ if(anEntry.Tag == theQuery.Entry.Tag
21
+ && (anEntry.Format == theQuery.Entry.Format || theQuery.Entry.Format == 0)) {
22
theQuery.Entry = anEntry;
23
theQuery.Folder = aDir.access();
24
return true;
25
sview-17_04.tar.gz/StShared/StFTFont.cpp -> sview-20_08.tar.gz/StShared/StFTFont.cpp
Changed
193
1
2
}
3
stMemZero(mySubsets, sizeof(mySubsets));
4
stMemZero(myFTFaces, sizeof(myFTFaces));
5
+ stMemZero(myFontFaces, sizeof(myFontFaces));
6
}
7
8
StFTFont::~StFTFont() {
9
10
aFace = NULL;
11
}
12
myFontPaths[aStyleIt].clear();
13
+ myFontFaces[aStyleIt] = 0;
14
}
15
}
16
17
18
}
19
20
if(myFTFaces[theStyle] != NULL) {
21
+ myUChar = 0;
22
myStyle = theStyle;
23
myFTFace = myFTFaces[theStyle];
24
return true;
25
26
return true;
27
}
28
29
-bool StFTFont::load(const StString& theFontPath,
30
- const StFTFont::Style theStyle) {
31
+bool StFTFont::load(const StString& theFontPath,
32
+ const int theFaceId,
33
+ const StFTFont::Style theStyle,
34
+ const bool theToSyntItalic) {
35
if(!myFTLib->isValid()
36
|| theStyle < Style_Regular
37
|| theStyle >= StylesNB
38
39
myFTFace = NULL;
40
myGlyphImg.nullify();
41
myFontPaths[theStyle] = theFontPath;
42
+ myFontFaces[theStyle] = theFaceId;
43
44
FT_Face& aFace = myFTFaces[theStyle];
45
if(aFace != NULL) {
46
FT_Done_Face(aFace);
47
}
48
const StString aFontPath = StFileNode::getCompatibleName(theFontPath);
49
- if(FT_New_Face(myFTLib->getInstance(), aFontPath.toCString(), 0, &aFace) != 0) {
50
+ if(FT_New_Face(myFTLib->getInstance(), aFontPath.toCString(), (FT_Long )theFaceId, &aFace) != 0) {
51
ST_DEBUG_LOG("Font '" + aFontPath + "' fail to load!");
52
FT_Done_Face(aFace);
53
aFace = NULL;
54
return false;
55
}
56
+
57
+ if(theToSyntItalic) {
58
+ const double THE_SHEAR_ANGLE = 10.0 * M_PI / 180.0;
59
+
60
+ FT_Matrix aMat;
61
+ aMat.xx = FT_Fixed(std::cos(-THE_SHEAR_ANGLE) * (1 << 16));
62
+ aMat.xy = 0;
63
+ aMat.yx = 0;
64
+ aMat.yy = aMat.xx;
65
+
66
+ FT_Fixed aFactor = FT_Fixed(std::tan(THE_SHEAR_ANGLE) * (1 << 16));
67
+ aMat.xy += FT_MulFix(aFactor, aMat.xx);
68
+
69
+ FT_Set_Transform(aFace, &aMat, 0);
70
+ }
71
return loadCharmap(aFontPath, aFace);
72
}
73
74
75
myFTFace = NULL;
76
myGlyphImg.nullify();
77
myFontPaths[theStyle] = theFontName;
78
+ myFontFaces[theStyle] = 0;
79
80
FT_Face& aFace = myFTFaces[theStyle];
81
if(aFace != NULL) {
82
83
84
// test Unicode subsets
85
mySubsets[Subset_General] = true;
86
- mySubsets[Subset_Korean] = FT_Get_Char_Index(theFace, 0x0B371) != 0
87
- && FT_Get_Char_Index(theFace, 0x0D130) != 0;
88
- mySubsets[Subset_CJK] = FT_Get_Char_Index(theFace, 0x06F22) != 0;
89
-
90
-//if(mySubsets[Subset_Korean]) { std::cerr << " found Korean in " << myFontPath << "\n"; }
91
-//if(mySubsets[Subset_CJK]) { std::cerr << " found CJK in " << myFontPath << "\n"; }
92
-
93
+ mySubsets[Subset_Korean] = FT_Get_Char_Index(theFace, 0x0B371) != 0
94
+ && FT_Get_Char_Index(theFace, 0x0D130) != 0;
95
+ mySubsets[Subset_CJK] = FT_Get_Char_Index(theFace, 0x06F22) != 0;
96
+ mySubsets[Subset_Arabic] = FT_Get_Char_Index(theFace, 0x00600) != 0;
97
+ mySubsets[Subset_MiscSymbols] = FT_Get_Char_Index(theFace, 0x0266A) != 0;
98
return true;
99
}
100
101
102
addAdvanceY(theUCharNext, thePen);
103
}
104
105
-float StFTFont::getAdvanceX(const stUtf32_t theUCharNext) {
106
+bool StFTFont::getKerning(FT_Vector& theKern,
107
+ const stUtf32_t theUCharCurr,
108
+ const stUtf32_t theUCharNext) const {
109
+ theKern.x = 0;
110
+ theKern.y = 0;
111
+ if(theUCharNext != 0 && FT_HAS_KERNING(myFTFace) != 0) {
112
+ const FT_UInt aCharCurr = FT_Get_Char_Index(myFTFace, theUCharCurr);
113
+ const FT_UInt aCharNext = FT_Get_Char_Index(myFTFace, theUCharNext);
114
+ if(aCharCurr == 0 || aCharNext == 0
115
+ || FT_Get_Kerning (myFTFace, aCharCurr, aCharNext, FT_KERNING_UNFITTED, &theKern) != 0) {
116
+ theKern.x = 0;
117
+ theKern.y = 0;
118
+ return false;
119
+ }
120
+ return true;
121
+ }
122
+ return false;
123
+}
124
+
125
+float StFTFont::getAdvanceX(const stUtf32_t theUCharNext) const {
126
if(myUChar == 0) {
127
return 0.0f;
128
}
129
130
- if(FT_HAS_KERNING(myFTFace) == 0 || theUCharNext == 0
131
- || FT_Get_Kerning(myFTFace, myUChar, theUCharNext, FT_KERNING_UNFITTED, &myKernAdvance) != 0) {
132
- return float(myFTFace->glyph->advance.x) / 64.0f;
133
- }
134
- return float(myKernAdvance.x + myFTFace->glyph->advance.x) / 64.0f;
135
+ FT_Vector aKern;
136
+ getKerning(aKern, myUChar, theUCharNext);
137
+ return float(aKern.x + myFTFace->glyph->advance.x) / 64.0f;
138
}
139
140
-float StFTFont::getAdvanceY(const stUtf32_t theUCharNext) {
141
+float StFTFont::getAdvanceY(const stUtf32_t theUCharNext) const {
142
if(myUChar == 0) {
143
return 0.0f;
144
}
145
146
- if(FT_HAS_KERNING(myFTFace) == 0 || theUCharNext == 0
147
- || FT_Get_Kerning(myFTFace, myUChar, theUCharNext, FT_KERNING_UNFITTED, &myKernAdvance) != 0) {
148
- return float(myFTFace->glyph->advance.y) / 64.0f;
149
- }
150
- return float(myKernAdvance.y + myFTFace->glyph->advance.y) / 64.0f;
151
+ FT_Vector aKern;
152
+ getKerning(aKern, myUChar, theUCharNext);
153
+ return float(aKern.y + myFTFace->glyph->advance.y) / 64.0f;
154
}
155
156
void StFTFont::addAdvanceX(const stUtf32_t theUCharNext,
157
- StVec2<GLfloat>& thePen) {
158
+ StVec2<GLfloat>& thePen) const {
159
if(myUChar == 0) {
160
return;
161
}
162
163
- if(FT_HAS_KERNING(myFTFace) == 0 || theUCharNext == 0
164
- || FT_Get_Kerning(myFTFace, myUChar, theUCharNext, FT_KERNING_UNFITTED, &myKernAdvance) != 0) {
165
- thePen.x() += float(myFTFace->glyph->advance.x) / 64.0f;
166
- } else {
167
- thePen.x() += float(myKernAdvance.x + myFTFace->glyph->advance.x) / 64.0f;
168
- }
169
+ FT_Vector aKern;
170
+ getKerning(aKern, myUChar, theUCharNext);
171
+ thePen.x() += float(aKern.x + myFTFace->glyph->advance.x) / 64.0f;
172
}
173
174
void StFTFont::addAdvanceY(const stUtf32_t theUCharNext,
175
- StVec2<GLfloat>& thePen) {
176
+ StVec2<GLfloat>& thePen) const {
177
if(myUChar == 0) {
178
return;
179
}
180
181
- if(FT_HAS_KERNING(myFTFace) == 0 || theUCharNext == 0
182
- || FT_Get_Kerning(myFTFace, myUChar, theUCharNext, FT_KERNING_UNFITTED, &myKernAdvance) != 0) {
183
- thePen.y() += float(myFTFace->glyph->advance.y) / 64.0f;
184
- } else {
185
- thePen.y() += float(myKernAdvance.y + myFTFace->glyph->advance.y) / 64.0f;
186
- }
187
+ FT_Vector aKern;
188
+ getKerning(aKern, myUChar, theUCharNext);
189
+ thePen.y() += float(aKern.y + myFTFace->glyph->advance.y) / 64.0f;
190
}
191
192
bool StFTFont::hasSymbol(const stUtf32_t theUChar) const {
193
sview-17_04.tar.gz/StShared/StFTFontRegistry.cpp -> sview-20_08.tar.gz/StShared/StFTFontRegistry.cpp
Changed
331
1
2
#include <StThreads/StProcess.h>
3
#include <stAssert.h>
4
5
+#if !defined(_WIN32) && !defined(__ANDROID__) && !defined(__APPLE__) && !defined(__EMSCRIPTEN__)
6
+ // use fontconfig library on Linux
7
+ #include <fontconfig/fontconfig.h>
8
+#endif
9
+
10
namespace {
11
- const StFTFontFamily THE_NO_FAMILY;
12
-};
13
+ static const StFTFontFamily THE_NO_FAMILY;
14
+}
15
16
StFTFontRegistry::StFTFontRegistry() {
17
myFTLib = new StFTLibrary();
18
19
myFolders.add(stCString("/Library/Fonts"));
20
21
// western
22
- myFilesMajor.add(stCString("Times.dfont"));
23
+ myFilesMinor.add(stCString("Times.dfont")); // old macOS
24
+ myFilesMajor.add(stCString("Times.ttc"));
25
myFilesMajor.add(stCString("Times New Roman.ttf"));
26
myFilesMajor.add(stCString("Times New Roman Bold.ttf"));
27
myFilesMajor.add(stCString("Times New Roman Italic.ttf"));
28
29
//myFilesMajor.add(stCString("AppleMyungjo.ttf"));
30
myFilesMajor.add(stCString("AppleGothic.ttf"));
31
// chinese
32
- myFilesMajor.add(stCString("华文仿宋.ttf"));
33
+ myFilesMinor.add(stCString("华文仿宋.ttf")); // old macOS
34
+ myFilesMajor.add(stCString("Songti.ttc"));
35
#elif defined(__ANDROID__)
36
myFolders.add(stCString("/system/fonts"));
37
38
39
myFilesMajor.add(stCString("DroidSansMono.ttf"));
40
41
// not all phones have the following fonts
42
+ myFilesMinor.add(stCString("NotoSansCJK-Regular.ttc"));
43
44
// Korean
45
myFilesMinor.add(stCString("NanumGothic.ttf"));
46
47
48
// Japanese
49
//myFilesMinor.add(stCString("NotoSansJP-Regular.otf"));
50
+
51
+ // Arabic
52
+ myFilesMinor.add(stCString("NotoNaskhArabic-Regular.ttf"));
53
+ //myFilesMinor.add(stCString("NotoNaskhArabic-Bold.ttf"));
54
#else
55
- myFolders.add(stCString("/usr/share/fonts"));
56
- myFolders.add(stCString("/usr/local/share/fonts"));
57
+
58
+#if !defined(__EMSCRIPTEN__)
59
+ if(FcConfig* aFcCfg = FcInitLoadConfig()) {
60
+ if(FcStrList* aFcFontDir = FcConfigGetFontDirs(aFcCfg)) {
61
+ for(;;) {
62
+ FcChar8* aFcFolder = FcStrListNext(aFcFontDir);
63
+ if(aFcFolder == NULL) {
64
+ break;
65
+ }
66
+
67
+ myFolders.add(StString((const char* )aFcFolder));
68
+ }
69
+ FcStrListDone(aFcFontDir);
70
+ }
71
+ FcConfigDestroy(aFcCfg);
72
+ }
73
+#endif
74
+ if(myFolders.isEmpty()) {
75
+ myFolders.add(stCString("/usr/share/fonts"));
76
+ myFolders.add(stCString("/usr/local/share/fonts"));
77
+ }
78
79
// western
80
myFilesMajor.add(stCString("DejaVuSerif.ttf"));
81
82
myFilesMajor.add(stCString("NanumMyeongjoBold.ttf"));
83
myFilesMajor.add(stCString("NanumGothic.ttf"));
84
myFilesMajor.add(stCString("NanumGothicBold.ttf"));
85
+ myFilesMinor.add(stCString("NotoSerifCJK-Regular.ttc"));
86
87
// chinese
88
//myFilesMajor.add(stCString("DroidSansJapanese.ttf"));
89
90
myFolders.add(theFolder);
91
}
92
93
+bool StFTFontRegistry::registerFamily(const StString& theFontPath, int theFaceId) {
94
+ const FT_Long aFaceId = theFaceId != -1 ? theFaceId : 0;
95
+ FT_Face aFace = NULL;
96
+ if(FT_New_Face(myFTLib->getInstance(), theFontPath.toCString(), aFaceId, &aFace) != 0) {
97
+ if(aFace != NULL) {
98
+ FT_Done_Face(aFace);
99
+ }
100
+ return false;
101
+ }
102
+ if(aFace->family_name == NULL // skip broken fonts (error in FreeType?)
103
+ || FT_Select_Charmap(aFace, ft_encoding_unicode) != 0) { // handle only UNICODE fonts
104
+ FT_Done_Face(aFace);
105
+ return false;
106
+ }
107
+
108
+ // generate font family name
109
+ StString aStyle(aFace->style_name != NULL ? aFace->style_name : "");
110
+ {
111
+ // remove standard style combinations reflected by style_flags
112
+ // and keep only extra styles like Light, Condensed and similar
113
+ static const StString THE_EMPTY;
114
+ static const StString THE_SPACE1(" ");
115
+ static const StString THE_SPACE2(" ");
116
+ static const StString THE_ITALIC1("Italic");
117
+ static const StString THE_ITALIC2("Oblique");
118
+ static const StString THE_BOLD("Bold");
119
+ static const StString THE_REGULAR1("Regular");
120
+ static const StString THE_REGULAR2("Book");
121
+ if(aFace->style_flags == (FT_STYLE_FLAG_ITALIC | FT_STYLE_FLAG_BOLD)) {
122
+ aStyle = aStyle.replace(THE_BOLD, THE_EMPTY);
123
+ const size_t aLen = aStyle.Length;
124
+ aStyle = aStyle.replace(THE_ITALIC1, THE_EMPTY);
125
+ if(aLen == aStyle.Length) {
126
+ aStyle = aStyle.replace(THE_ITALIC2, THE_EMPTY);
127
+ }
128
+ } else if(aFace->style_flags == FT_STYLE_FLAG_BOLD) {
129
+ aStyle = aStyle.replace(THE_BOLD, THE_EMPTY);
130
+ } else if(aFace->style_flags == FT_STYLE_FLAG_ITALIC) {
131
+ const size_t aLen = aStyle.Length;
132
+ aStyle = aStyle.replace(THE_ITALIC1, THE_EMPTY);
133
+ if(aLen == aStyle.Length) {
134
+ aStyle = aStyle.replace(THE_ITALIC2, THE_EMPTY);
135
+ }
136
+ }
137
+ const size_t aLen2 = aStyle.Length;
138
+ aStyle = aStyle.replace(THE_REGULAR1, THE_EMPTY);
139
+ if(aLen2 == aStyle.Length) {
140
+ aStyle = aStyle.replace(THE_REGULAR2, THE_EMPTY);
141
+ }
142
+ aStyle.leftAdjust();
143
+ aStyle.rightAdjust();
144
+ aStyle.replace(THE_SPACE2, THE_SPACE1);
145
+ }
146
+
147
+ StString aFamilyName = aFace->family_name;
148
+ if(!aStyle.isEmpty()) {
149
+ aFamilyName = aFamilyName + " " + aStyle;
150
+ }
151
+
152
+ StFTFontFamily& aFamily = myFonts[aFamilyName];
153
+ aFamily.FamilyName = aFamilyName;
154
+ if(aFace->style_flags == (FT_STYLE_FLAG_ITALIC | FT_STYLE_FLAG_BOLD)) {
155
+ aFamily.BoldItalic = theFontPath;
156
+ aFamily.BoldItalicFace = (int )aFaceId;
157
+ } else if(aFace->style_flags == FT_STYLE_FLAG_BOLD) {
158
+ aFamily.Bold = theFontPath;
159
+ aFamily.BoldFace = (int )aFaceId;
160
+ } else if(aFace->style_flags == FT_STYLE_FLAG_ITALIC) {
161
+ aFamily.Italic = theFontPath;
162
+ aFamily.ItalicFace = (int )aFaceId;
163
+ } else {
164
+ aFamily.Regular = theFontPath;
165
+ aFamily.RegularFace = (int )aFaceId;
166
+ }
167
+ //ST_DEBUG_LOG("StFTFontRegistry, font file '" + theFontPath + " [" + aFaceId + "]" + "', family '" + aFamily.FamilyName + "', contains " + aFace->num_glyphs + " glyphs!");
168
+
169
+ if(theFaceId < aFace->num_faces) {
170
+ const FT_Long aNbInstances = aFace->style_flags >> 16;
171
+ for(FT_Long anInstIter = 1; anInstIter < aNbInstances; ++anInstIter) {
172
+ const FT_Long aSubFaceId = aFaceId + (anInstIter << 16);
173
+ registerFamily(theFontPath, aSubFaceId);
174
+ }
175
+ }
176
+ if(theFaceId == -1) {
177
+ for(FT_Long aFaceIter = 1; aFaceIter < aFace->num_faces; ++aFaceIter) {
178
+ registerFamily(theFontPath, aFaceIter);
179
+ }
180
+ }
181
+ FT_Done_Face(aFace);
182
+ return true;
183
+}
184
+
185
void StFTFontRegistry::searchFiles(const StArrayList<StString>& theNames,
186
const bool theIsMajor) {
187
for(size_t aNameIter = 0; aNameIter < theNames.size(); ++aNameIter) {
188
189
continue;
190
}
191
192
- FT_Face aFace = NULL;
193
- if(FT_New_Face(myFTLib->getInstance(), aPath.toCString(), 0, &aFace) != 0) {
194
+ if(!registerFamily(aPath, -1)) {
195
if(theIsMajor) {
196
ST_ERROR_LOG("StFTFontRegistry, major font file '" + aName + "' fail to load"
197
+ " from path '" + aPath + "'!");
198
}
199
- if(aFace != NULL) {
200
- FT_Done_Face(aFace);
201
- }
202
continue;
203
}
204
-
205
- StFTFontFamily& aFamily = myFonts[aFace->family_name];
206
- aFamily.FamilyName = aFace->family_name;
207
- if(aFace->style_flags == (FT_STYLE_FLAG_ITALIC | FT_STYLE_FLAG_BOLD)) {
208
- aFamily.BoldItalic = aPath;
209
- } else if(aFace->style_flags == FT_STYLE_FLAG_BOLD) {
210
- aFamily.Bold = aPath;
211
- } else if(aFace->style_flags == FT_STYLE_FLAG_ITALIC) {
212
- aFamily.Italic = aPath;
213
- } else {
214
- aFamily.Regular = aPath;
215
- }
216
- //ST_DEBUG_LOG("StFTFontRegistry, font file '" + aName + "', family '" + aFamily.FamilyName + "', contains " + aFace->num_glyphs + " glyphs!");
217
-
218
- FT_Done_Face(aFace);
219
}
220
}
221
222
223
aSerif.Western = findFont(stCString("Times New Roman"));
224
aSans .Western = findFont(stCString("Trebuchet MS"));
225
aMono .Western = findFont(stCString("Tahoma"));
226
+ aSans.MiscSymbols = aSerif.Western; // Trebuchet font does not include this sub-set
227
const StFTFontFamily& aMalgun = findFont(stCString("Malgun Gothic"));
228
const StFTFontFamily& aGulim = findFont(stCString("Gulim"));
229
const StFTFontFamily& aKor = aMalgun.FamilyName.isEmpty() && !aGulim.FamilyName.isEmpty()
230
? aGulim
231
: aMalgun;
232
+ const StFTFontFamily& anArabic = findFont(stCString("Times New Roman"));
233
+ aSerif.Arabic = anArabic;
234
+ aSans .Arabic = anArabic;
235
+ aMono .Arabic = anArabic;
236
aSerif.Korean = aKor;
237
aSans .Korean = aKor;
238
aMono .Korean = aKor;
239
240
aSerif.Korean = findFont(stCString("AppleGothic")); // AppleMyungjo can not be loaded
241
aSans .Korean = findFont(stCString("AppleGothic"));
242
aMono .Korean = findFont(stCString("AppleGothic"));
243
- aSerif.CJK = findFont(stCString("STFangsong"));
244
- aSans .CJK = findFont(stCString("STFangsong"));
245
- aMono .CJK = findFont(stCString("STFangsong"));
246
+ const StFTFontFamily& aSongtiSC = findFont(stCString("Songti SC Light"));
247
+ const StFTFontFamily& aFang = findFont(stCString("STFangsong"));
248
+ const StFTFontFamily& aCjk = aSongtiSC.FamilyName.isEmpty() && !aFang.FamilyName.isEmpty()
249
+ ? aFang
250
+ : aSongtiSC;
251
+ aSerif.CJK = aCjk;
252
+ aSans .CJK = aCjk;
253
+ aMono .CJK = aCjk;
254
+ aSerif.Arabic = findFont(stCString("DecoType Naskh"));
255
+ aSans .Arabic = findFont(stCString("DecoType Naskh"));
256
+ aMono .Arabic = findFont(stCString("DecoType Naskh"));
257
#elif defined(__ANDROID__)
258
aSerif.Western = findFont(stCString("Noto Serif"));
259
if(aSerif.Western.FamilyName.isEmpty()) {
260
261
}
262
aSans .Western = findFont(stCString("Roboto")); // actually DroidSans.ttf
263
aMono .Western = findFont(stCString("Droid Sans Mono"));
264
+
265
aSerif.Korean = findFont(stCString("NanumGothic")); // no serif
266
- aSans .Korean = findFont(stCString("NanumGothic"));
267
- aMono .Korean = findFont(stCString("NanumGothic"));
268
+ aSans .Korean = aSerif.Korean;
269
+ aMono .Korean = aSerif.Korean;
270
if(aSerif.Korean.FamilyName.isEmpty()) {
271
aSerif.Korean = findFont(stCString("Noto Sans KR"));
272
- aSans .Korean = findFont(stCString("Noto Sans KR"));
273
- aMono .Korean = findFont(stCString("Noto Sans KR"));
274
+ aSans .Korean = aSerif.Korean;
275
+ aMono .Korean = aSerif.Korean;
276
}
277
aSerif.CJK = findFont(stCString("Droid Sans Fallback"));
278
- aSans .CJK = findFont(stCString("Droid Sans Fallback"));
279
- aMono .CJK = findFont(stCString("Droid Sans Fallback"));
280
+ aSans .CJK = aSerif.CJK;
281
+ aMono .CJK = aSerif.CJK;
282
if(aSerif.CJK.FamilyName.isEmpty()) {
283
aSerif.CJK = findFont(stCString("Noto Sans SC"));
284
- aSans .CJK = findFont(stCString("Noto Sans SC"));
285
- aMono .CJK = findFont(stCString("Noto Sans SC"));
286
+ aSans .CJK = aSerif.CJK;
287
+ aMono .CJK = aSerif.CJK;
288
+ }
289
+ if(aSerif.CJK.FamilyName.isEmpty()) {
290
+ aSerif.CJK = findFont(stCString("Noto Sans CJK JP"));
291
+ aSans .CJK = aSerif.CJK;
292
+ aMono .CJK = aSerif.CJK;
293
+ }
294
+ if(aSerif.Korean.FamilyName.isEmpty()) {
295
+ aSerif.Korean = aSerif.CJK;
296
+ aSans .Korean = aSerif.CJK;
297
+ aMono .Korean = aSerif.CJK;
298
+ }
299
+
300
+ aSerif.Arabic = findFont(stCString("Droid Arabic Naskh"));
301
+ aSans .Arabic = aSerif.Arabic;
302
+ aMono .Arabic = aSerif.Arabic;
303
+ if(aSerif.Arabic.FamilyName.isEmpty()) {
304
+ aSerif.Arabic = findFont(stCString("Noto Naskh Arabic"));
305
+ aSans .Arabic = aSerif.Arabic;
306
+ aMono .Arabic = aSerif.Arabic;
307
}
308
#else
309
aSerif.Western = findFont(stCString("FreeSerif"));
310
311
aSans .Western = findFont(stCString("DejaVu Sans"));
312
}
313
aMono .Western = findFont(stCString("DejaVu Sans Mono"));
314
- aSerif.Korean = findFont(stCString("NanumMyeongjo"));
315
- aSans .Korean = findFont(stCString("NanumGothic"));
316
- aMono .Korean = findFont(stCString("NanumGothic"));
317
+
318
+ const StFTFontFamily& aNanumMyeon = findFont(stCString("NanumMyeongjo"));
319
+ const StFTFontFamily& aNotoSerifCjkJp = findFont(stCString("Noto Serif CJK JP"));
320
+ const StFTFontFamily& aNanumGoth = findFont(stCString("NanumGothic"));
321
+ aSerif.Korean = aNanumMyeon.FamilyName.isEmpty() && !aNotoSerifCjkJp.FamilyName.isEmpty()
322
+ ? aNotoSerifCjkJp
323
+ : aNanumMyeon;;
324
+ aSans .Korean = aNanumGoth.FamilyName.isEmpty() && !aNotoSerifCjkJp.FamilyName.isEmpty()
325
+ ? aNotoSerifCjkJp
326
+ : aNanumGoth;
327
+ aMono .Korean = aSans.Korean;
328
aSerif.CJK = findFont(stCString("Droid Sans Fallback"));
329
aSans .CJK = findFont(stCString("Droid Sans Fallback"));
330
aMono .CJK = findFont(stCString("Droid Sans Fallback"));
331
sview-17_04.tar.gz/StShared/StFileNode.ObjC.mm -> sview-20_08.tar.gz/StShared/StFileNode.ObjC.mm
Changed
66
1
2
#if (defined(__APPLE__))
3
4
#include <StFile/StFileNode.h>
5
-#include <StFile/StMIMEList.h>
6
7
#include <StCocoa/StCocoaLocalPool.h>
8
9
10
[aFilePanel setAllowedFileTypes: myFilter];
11
}
12
13
+ ST_DISABLE_DEPRECATION_WARNINGS
14
if([aFilePanel runModal] == NSOKButton) {
15
myIsFileSelected = true;
16
// automatically convert filenames from decomposed form used by Mac OS X file systems
17
NSString* aFileName = [[aFilePanel filename] precomposedStringWithCanonicalMapping];
18
myResult = [aFileName UTF8String];
19
}
20
+ ST_ENABLE_DEPRECATION_WARNINGS
21
}
22
23
@end
24
25
-bool StFileNode::openFileDialog(const StString& theFolder,
26
- const StString& theTitle,
27
- const StMIMEList& theFilter,
28
- StString& theFilePath,
29
- bool toSave) {
30
+bool StFileNode::openFileDialog(StString& theFilePath,
31
+ const StOpenFileName& theInfo,
32
+ bool theToSave) {
33
if(NSApp == nil) {
34
return false;
35
}
36
37
StFileNode::getFolderAndFile(theFilePath, aFolderSrc, aFileNameSrc);
38
39
StCocoaLocalPool aLocalPool;
40
- NSString* aTitle = [NSString stringWithUTF8String: theTitle.toCString()];
41
- NSString* aFolder = [NSString stringWithUTF8String: theFolder.toCString()];
42
+ NSString* aTitle = [NSString stringWithUTF8String: theInfo.Title.toCString()];
43
+ NSString* aFolder = [NSString stringWithUTF8String: theInfo.Folder.toCString()];
44
NSString* anInitFile = [NSString stringWithUTF8String: aFileNameSrc.toCString()];
45
NSMutableArray* aFilter = NULL;
46
- if(!theFilter.isEmpty()) {
47
- aFilter = [NSMutableArray arrayWithCapacity: theFilter.size()];
48
- for(size_t aMimeId = 0; aMimeId < theFilter.size(); ++aMimeId) {
49
- const StMIME& aMime = theFilter[aMimeId];
50
+ if(!theInfo.Filter.isEmpty()) {
51
+ aFilter = [NSMutableArray arrayWithCapacity: theInfo.Filter.size()];
52
+ for(size_t aMimeId = 0; aMimeId < theInfo.Filter.size(); ++aMimeId) {
53
+ const StMIME& aMime = theInfo.Filter[aMimeId];
54
[aFilter addObject: [NSString stringWithUTF8String: aMime.getExtension().toCString()]];
55
}
56
}
57
58
withTitle: aTitle
59
withFolder: aFolder
60
withFile: anInitFile
61
- toSave: toSave];
62
+ toSave: theToSave];
63
if([NSThread isMainThread]) {
64
[anOpenFile doDialog: NULL];
65
} else {
66
sview-17_04.tar.gz/StShared/StFileNode.cpp -> sview-20_08.tar.gz/StShared/StFileNode.cpp
Changed
46
1
2
/**
3
- * Copyright © 2010-2013 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2010-2017 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* Distributed under the Boost Software License, Version 1.0.
7
* See accompanying file license-boost.txt or copy at
8
9
#endif
10
}
11
12
+bool StFileNode::isFileReadOnly(const StCString& thePath) {
13
+#ifdef _WIN32
14
+ StStringUtfWide aPath;
15
+ aPath.fromUnicode(thePath);
16
+ DWORD anAttribs = ::GetFileAttributesW(aPath.toCString());
17
+ return (anAttribs & FILE_ATTRIBUTE_READONLY) != 0;
18
+#else
19
+ // not implemented
20
+ return false;
21
+#endif
22
+}
23
+
24
+bool StFileNode::removeReadOnlyFlag(const StCString& thePath) {
25
+#ifdef _WIN32
26
+ StStringUtfWide aPath;
27
+ aPath.fromUnicode(thePath);
28
+ DWORD anAttribs = ::GetFileAttributesW(aPath.toCString());
29
+ if(anAttribs == INVALID_FILE_ATTRIBUTES) {
30
+ return false;
31
+ } else if((anAttribs & FILE_ATTRIBUTE_READONLY) == 0) {
32
+ return true;
33
+ }
34
+
35
+ anAttribs = (anAttribs & ~FILE_ATTRIBUTE_READONLY);
36
+ return ::SetFileAttributesW(aPath.toCString(), anAttribs) != FALSE;
37
+#else
38
+ // not implemented
39
+ return false;
40
+#endif
41
+}
42
+
43
bool StFileNode::removeFile(const StCString& thePath) {
44
#ifdef _WIN32
45
StStringUtfWide aPath;
46
sview-17_04.tar.gz/StShared/StFileNode2.cpp -> sview-20_08.tar.gz/StShared/StFileNode2.cpp
Changed
126
1
2
#ifndef __APPLE__
3
4
#include <StFile/StFileNode.h>
5
-#include <StFile/StMIMEList.h>
6
#include <StStrings/StLogger.h>
7
8
#ifdef _WIN32
9
10
* in commonly used class.
11
* This needed only for Windows.
12
*/
13
-bool StFileNode::openFileDialog(const StString& theFolder,
14
- const StString& theTitle,
15
- const StMIMEList& theFilter,
16
- StString& theFilePath,
17
- bool toSave) {
18
+bool StFileNode::openFileDialog(StString& theFilePath,
19
+ const StOpenFileName& theInfo,
20
+ bool theToSave) {
21
#ifdef _WIN32
22
- const StStringUtfWide aFolder = theFolder.toUtfWide();
23
- const StStringUtfWide aTitle = theTitle.toUtfWide();
24
+ const StStringUtfWide aFolder = theInfo.Folder.toUtfWide();
25
+ const StStringUtfWide aTitle = theInfo.Title.toUtfWide();
26
27
// use dummy \n symbol instead of NULL-termination symbol \0 inside string
28
// because such string will be invalid for StString class
29
const StStringUtfWide NULL_CHAR = '\n';
30
31
- StStringUtfWide aFilterString;
32
- StStringUtfWide anAllSupportedExt;
33
- for(size_t aMimeId = 0; aMimeId < theFilter.size(); ++aMimeId) {
34
- const StMIME& aMime = theFilter[aMimeId];
35
+ StStringUtfWide aFilterString, anAllSupportedExt, anExtraSupportedExt;
36
+ for(size_t aMimeId = 0; aMimeId < theInfo.Filter.size(); ++aMimeId) {
37
+ const StMIME& aMime = theInfo.Filter[aMimeId];
38
if(aMimeId > 0) {
39
anAllSupportedExt += StStringUtfWide(';');
40
}
41
42
}
43
44
// fill 'All supported'
45
- if(!anAllSupportedExt.isEmpty() && theFilter.size() > 1) {
46
- aFilterString += StStringUtfWide(L"All supported\n");
47
+ if(!anAllSupportedExt.isEmpty() && theInfo.Filter.size() > 1) {
48
+ if(!theInfo.FilterTitle.isEmpty()) {
49
+ aFilterString += theInfo.FilterTitle.toUtfWide();
50
+ } else {
51
+ aFilterString += StStringUtfWide(L"All supported");
52
+ }
53
+ aFilterString += StStringUtfWide(L"\n");
54
aFilterString += anAllSupportedExt + NULL_CHAR;
55
}
56
57
+ // fill 'Extra supported'
58
+ for(size_t aMimeId = 0; aMimeId < theInfo.ExtraFilter.size(); ++aMimeId) {
59
+ const StMIME& aMime = theInfo.ExtraFilter[aMimeId];
60
+ if(aMimeId > 0) {
61
+ anExtraSupportedExt += StStringUtfWide(';');
62
+ }
63
+ anExtraSupportedExt += StStringUtfWide(L"*.") + aMime.getExtension().toUtfWide();
64
+ }
65
+ if(!anExtraSupportedExt.isEmpty() && theInfo.ExtraFilter.size() > 1) {
66
+ if(!theInfo.ExtraFilterTitle.isEmpty()) {
67
+ aFilterString += theInfo.ExtraFilterTitle.toUtfWide();
68
+ } else {
69
+ aFilterString += StStringUtfWide(L"Extra supported");
70
+ }
71
+ aFilterString += StStringUtfWide(L"\n");
72
+ aFilterString += anExtraSupportedExt + NULL_CHAR;
73
+ }
74
+
75
// fill MIME types
76
- for(size_t aMimeId = 0; aMimeId < theFilter.size(); ++aMimeId) {
77
- const StMIME& aMime = theFilter[aMimeId];
78
- if((aMimeId > 0) && (aMime.getDescription() == theFilter[aMimeId - 1].getDescription())) {
79
+ for(size_t aMimeId = 0; aMimeId < theInfo.Filter.size(); ++aMimeId) {
80
+ const StMIME& aMime = theInfo.Filter[aMimeId];
81
+ if((aMimeId > 0) && (aMime.getDescription() == theInfo.Filter[aMimeId - 1].getDescription())) {
82
// append extension to previous MIME (prevent duplication)
83
aFilterString = aFilterString.subString(0, aFilterString.getLength() - 1); // backstep
84
aFilterString += StStringUtfWide(L";*.") + aMime.getExtension().toUtfWide() + NULL_CHAR;
85
86
}
87
88
// fill 'Any File'
89
- aFilterString += StStringUtfWide(L"Any File (*)\n");
90
+ aFilterString += StStringUtfWide(L"All Files (*)\n");
91
aFilterString += StStringUtfWide(L"*\n"); // last string should be terminated by \0\0
92
93
// replace dummy CR symbol within '\0' using 'hack' code
94
95
anOpenStruct.nMaxFileTitle = sizeof(aFileTitle);
96
anOpenStruct.lpstrTitle = aTitle.toCString();
97
anOpenStruct.Flags = OFN_PATHMUSTEXIST | OFN_FILEMUSTEXIST;
98
- if(!toSave) {
99
+ if(!theToSave) {
100
if(GetOpenFileNameW(&anOpenStruct)
101
&& *anOpenStruct.lpstrFile != L'\0') {
102
theFilePath = StString(anOpenStruct.lpstrFile);
103
104
}
105
gdk_threads_enter();
106
bool isFileSelected = false;
107
- GtkWidget* aDialog = gtk_file_chooser_dialog_new(theTitle.toCString(), NULL, (toSave ? GTK_FILE_CHOOSER_ACTION_SAVE : GTK_FILE_CHOOSER_ACTION_OPEN),
108
- GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL, (toSave ? GTK_STOCK_SAVE : GTK_STOCK_OPEN),
109
+ GtkWidget* aDialog = gtk_file_chooser_dialog_new(theInfo.Folder.toCString(), NULL, (theToSave ? GTK_FILE_CHOOSER_ACTION_SAVE : GTK_FILE_CHOOSER_ACTION_OPEN),
110
+ GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL, (theToSave ? GTK_STOCK_SAVE : GTK_STOCK_OPEN),
111
GTK_RESPONSE_ACCEPT, NULL);
112
- gtk_file_chooser_set_current_folder(GTK_FILE_CHOOSER(aDialog), theFolder.toCString());
113
+ gtk_file_chooser_set_current_folder(GTK_FILE_CHOOSER(aDialog), theInfo.Folder.toCString());
114
if(!theFilePath.isEmpty()) {
115
gtk_file_chooser_set_filename(GTK_FILE_CHOOSER(aDialog), theFilePath.toCString());
116
}
117
118
GtkFileFilter* gtkFilter = gtk_file_filter_new();
119
- for(size_t aMimeId = 0; aMimeId < theFilter.size(); ++aMimeId) {
120
- const StMIME& aMime = theFilter[aMimeId];
121
+ for(size_t aMimeId = 0; aMimeId < theInfo.Filter.size(); ++aMimeId) {
122
+ const StMIME& aMime = theInfo.Filter[aMimeId];
123
gtk_file_filter_add_pattern(gtkFilter, (StString("*.") + aMime.getExtension()).toCString());
124
}
125
126
sview-17_04.tar.gz/StShared/StFolder.cpp -> sview-20_08.tar.gz/StShared/StFolder.cpp
Changed
24
1
2
/**
3
- * Copyright © 2009-2014 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2009-2017 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* Distributed under the Boost Software License, Version 1.0.
7
* See accompanying file license-boost.txt or copy at
8
9
}
10
return false;
11
#else
12
- DIR* aDir = opendir(thePath.toCString());
13
- if(aDir == NULL) {
14
- return false;
15
- }
16
- closedir(aDir);
17
- return true;
18
+ struct stat aStatBuffer;
19
+ return stat(thePath.toCString(), &aStatBuffer) == 0
20
+ && S_ISDIR(aStatBuffer.st_mode);
21
#endif
22
}
23
24
sview-17_04.tar.gz/StShared/StFormatEnum.cpp -> sview-20_08.tar.gz/StShared/StFormatEnum.cpp
Changed
18
1
2
}
3
4
StFormat st::formatFromName(const StString& theFileName,
5
+ const bool theToSwapJps,
6
bool& theIsAnamorph) {
7
StString aName, anExt;
8
StFileNode::getNameAndExtension(theFileName, aName, anExt);
9
10
if(anExt == stCString("pns")
11
|| anExt == stCString("jps")) {
12
theIsAnamorph = false;
13
- return StFormat_SideBySide_RL;
14
+ return theToSwapJps ? StFormat_SideBySide_LR : StFormat_SideBySide_RL;
15
}
16
17
// this is not optimized search, but should be OK for most use cases
18
sview-17_04.tar.gz/StShared/StFreeImage.cpp -> sview-20_08.tar.gz/StShared/StFreeImage.cpp
Changed
9
1
2
case StImageFile::ST_TYPE_JPS: return FIF_JPEG;
3
case StImageFile::ST_TYPE_EXR: return FIF_EXR;
4
case StImageFile::ST_TYPE_HDR: return FIF_HDR;
5
+ case StImageFile::ST_TYPE_DDS: return FIF_DDS;
6
default: return FIF_UNKNOWN;
7
}
8
}
9
sview-17_04.tar.gz/StShared/StGLContext.cpp -> sview-20_08.tar.gz/StShared/StGLContext.cpp
Changed
191
1
2
/**
3
- * Copyright © 2012-2016 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2012-2019 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* Distributed under the Boost Software License, Version 1.0.
7
* See accompanying file license-boost.txt or copy at
8
9
10
#include <StGLCore/StGLCore44.h>
11
#include <StGL/StGLArbFbo.h>
12
+#include <StGL/StGLTexture.h>
13
14
#include <StStrings/StDictionary.h>
15
#include <StStrings/StLogger.h>
16
17
arbFbo(NULL),
18
arbNPTW(false),
19
arbTexRG(false),
20
+ arbTexFloat(false),
21
arbTexClear(false),
22
#if defined(GL_ES_VERSION_2_0)
23
- hasUnpack(false),
24
hasHighp(false),
25
hasTexRGBA8(false),
26
extTexBGRA8(false),
27
+ extTexR16(false),
28
#else
29
- hasUnpack(true),
30
hasHighp(true),
31
hasTexRGBA8(true), // always available on desktop
32
extTexBGRA8(true),
33
+ extTexR16(true),
34
#endif
35
extAll(NULL),
36
extSwapTear(false),
37
+ khrFlushControl(false),
38
myFuncs(new StGLFunctions()),
39
myResMgr(theResMgr),
40
myGlVendor(GlVendor_UNKNOWN),
41
myGpuName(GPU_UNKNOWN),
42
myVerMajor(0),
43
myVerMinor(0),
44
- myMaxTexDim(0),
45
myWasInit(false),
46
myFramebufferDraw(0),
47
myFramebufferRead(0),
48
49
#ifdef __APPLE__
50
mySysLib.loadSimple("/System/Library/Frameworks/OpenGL.framework/Versions/Current/OpenGL");
51
#endif
52
+
53
+#if defined(GL_ES_VERSION_2_0)
54
+ myDevCaps.hasUnpack = false;
55
+#else
56
+ myDevCaps.hasUnpack = true;
57
+#endif
58
}
59
60
StGLContext::StGLContext(const bool theToInitialize)
61
62
arbFbo(NULL),
63
arbNPTW(false),
64
arbTexRG(false),
65
+ arbTexFloat(false),
66
arbTexClear(false),
67
#if defined(GL_ES_VERSION_2_0)
68
- hasUnpack(false),
69
hasHighp(false),
70
hasTexRGBA8(false),
71
extTexBGRA8(false),
72
+ extTexR16(false),
73
#else
74
- hasUnpack(true), // always available on desktop
75
hasHighp(true),
76
hasTexRGBA8(true),
77
extTexBGRA8(true),
78
+ extTexR16(true),
79
#endif
80
extAll(NULL),
81
extSwapTear(false),
82
+ khrFlushControl(false),
83
myFuncs(new StGLFunctions()),
84
myGlVendor(GlVendor_UNKNOWN),
85
myGpuName(GPU_UNKNOWN),
86
myVerMajor(0),
87
myVerMinor(0),
88
- myMaxTexDim(0),
89
myWasInit(false),
90
myFramebufferDraw(0),
91
myFramebufferRead(0),
92
93
#ifdef __APPLE__
94
mySysLib.loadSimple("/System/Library/Frameworks/OpenGL.framework/Versions/Current/OpenGL");
95
#endif
96
+
97
+#if defined(GL_ES_VERSION_2_0)
98
+ myDevCaps.hasUnpack = false;
99
+#else
100
+ myDevCaps.hasUnpack = true; // always available on desktop
101
+#endif
102
if(theToInitialize) {
103
stglInit();
104
}
105
106
theMap.add(StDictEntry("GLdevice", (const char* )glGetString(GL_RENDERER)));
107
theMap.add(StDictEntry("GLversion", (const char* )glGetString(GL_VERSION)));
108
theMap.add(StDictEntry("GLSLversion", (const char* )glGetString(GL_SHADING_LANGUAGE_VERSION)));
109
- theMap.add(StDictEntry("Max texture size", myMaxTexDim));
110
+ theMap.add(StDictEntry("Max texture size", myDevCaps.maxTexDim));
111
theMap.add(StDictEntry("Window Info", StString()
112
+ myViewport.width() + "x" + myViewport.height()
113
+ " RGB" + myWindowBits.RGB + " A" + myWindowBits.Alpha
114
115
core11 = (StGLCore11* )(&(*myFuncs));
116
core11fwd = (StGLCore11Fwd* )(&(*myFuncs));
117
118
- myMaxTexDim = 2048;
119
- glGetIntegerv(GL_MAX_TEXTURE_SIZE, &myMaxTexDim);
120
+ myDevCaps.maxTexDim = 2048;
121
+ glGetIntegerv(GL_MAX_TEXTURE_SIZE, &myDevCaps.maxTexDim);
122
123
#if !defined(GL_ES_VERSION_2_0)
124
bool has12 = false;
125
126
127
// retrieve platform-dependent extensions
128
#if defined(ST_HAVE_EGL)
129
- //const char* aEglExts = eglQueryString(eglGetCurrentDisplay(), EGL_EXTENSIONS);
130
+ const char* anEglExts = eglQueryString(eglGetCurrentDisplay(), EGL_EXTENSIONS);
131
+ khrFlushControl = stglCheckExtension(anEglExts, "EGL_KHR_context_flush_control");
132
#elif defined(_WIN32)
133
if(STGL_READ_FUNC(wglGetExtensionsStringARB)) {
134
const char* aWglExts = myFuncs->wglGetExtensionsStringARB(wglGetCurrentDC());
135
136
}
137
if(stglCheckExtension(aWglExts, "WGL_ARB_create_context_profile")) {
138
STGL_READ_FUNC(wglCreateContextAttribsARB);
139
+ khrFlushControl = stglCheckExtension(aWglExts, "WGL_ARB_context_flush_control");
140
}
141
extSwapTear = stglCheckExtension(aWglExts, "WGL_EXT_swap_control_tear");
142
if(stglCheckExtension(aWglExts, "WGL_NV_DX_interop")) {
143
144
STGL_READ_FUNC(glXQueryCurrentRendererStringMESA);
145
}
146
extSwapTear = stglCheckExtension(aGlxExts, "GLX_EXT_swap_control_tear");
147
+ khrFlushControl = stglCheckExtension(aGlxExts, "GLX_ARB_context_flush_control");
148
#endif
149
150
#if defined(GL_ES_VERSION_2_0)
151
152
hasTexRGBA8 = isGlGreaterEqual(3, 0)
153
|| stglCheckExtension("GL_OES_rgb8_rgba8");
154
extTexBGRA8 = stglCheckExtension("GL_EXT_texture_format_BGRA8888");
155
+ extTexR16 = stglCheckExtension("GL_EXT_texture_norm16");
156
arbTexRG = isGlGreaterEqual(3, 0)
157
|| stglCheckExtension("GL_EXT_texture_rg");
158
+ arbTexFloat = isGlGreaterEqual(3, 0);
159
const bool hasFBO = isGlGreaterEqual(2, 0)
160
|| stglCheckExtension("GL_OES_framebuffer_object");
161
- hasUnpack = isGlGreaterEqual(3, 0);
162
+ myDevCaps.hasUnpack = isGlGreaterEqual(3, 0);
163
164
if(isGlGreaterEqual(2, 0)) {
165
// enable compatible functions
166
167
#else
168
hasTexRGBA8 = true;
169
extTexBGRA8 = true;
170
+ extTexR16 = true;
171
arbNPTW = stglCheckExtension("GL_ARB_texture_non_power_of_two");
172
arbTexRG = stglCheckExtension("GL_ARB_texture_rg");
173
+ arbTexFloat = isGlGreaterEqual(3, 0)
174
+ || stglCheckExtension("GL_ARB_texture_float");
175
176
// load OpenGL 1.2 new functions
177
has12 = isGlGreaterEqual(1, 2)
178
179
}*/
180
}
181
182
+ for(int aFormatIter = 0; aFormatIter < StImagePlane::ImgNB; ++aFormatIter) {
183
+ const StImagePlane::ImgFormat aFormat = (StImagePlane::ImgFormat )aFormatIter;
184
+ GLint aDummy = 0;
185
+ myDevCaps.setSupportedFormat(aFormat, StGLTexture::getInternalFormat(*this, aFormat, aDummy));
186
+ }
187
+
188
// log OpenGL info
189
ST_DEBUG_LOG("Created new GL context:\n" + stglFullInfo());
190
191
sview-17_04.tar.gz/StShared/StGLFontManager.cpp -> sview-20_08.tar.gz/StShared/StGLFontManager.cpp
Changed
35
1
2
}
3
4
StHandle<StFTFont> aFontFt = new StFTFont(myFTLib);
5
- aFontFt->load(aFont.Regular, StFTFont::Style_Regular);
6
- aFontFt->load(aFont.Bold, StFTFont::Style_Bold);
7
- aFontFt->load(aFont.Italic, StFTFont::Style_Italic);
8
- aFontFt->load(aFont.BoldItalic, StFTFont::Style_BoldItalic);
9
+ const bool hasItalic = !aFont.Italic.isEmpty();
10
+ const bool hasBoldItalic = !aFont.BoldItalic.isEmpty();
11
+ aFontFt->load(aFont.Regular, aFont.RegularFace, StFTFont::Style_Regular);
12
+ aFontFt->load(aFont.Bold, aFont.BoldFace, StFTFont::Style_Bold);
13
+ aFontFt->load(hasItalic ? aFont.Italic : aFont.Regular,
14
+ hasItalic ? aFont.ItalicFace : aFont.RegularFace,
15
+ StFTFont::Style_Italic, !hasItalic);
16
+ aFontFt->load(hasBoldItalic ? aFont.BoldItalic : aFont.Bold,
17
+ hasBoldItalic ? aFont.BoldItalicFace : aFont.BoldFace,
18
+ StFTFont::Style_BoldItalic, !hasBoldItalic);
19
aFontFt->init(theSize, myResolution);
20
aFontGl = new StGLFontEntry(aFontFt);
21
return aFontGl;
22
23
aGenFont = findCreate(aPack.Western.FamilyName, theSize);
24
aFont->changeFont(StFTFont::Subset_CJK) = findCreate(aPack.CJK .FamilyName, theSize);
25
aFont->changeFont(StFTFont::Subset_Korean) = findCreate(aPack.Korean .FamilyName, theSize);
26
+ if(aGenFont.isNull() || !aGenFont->hasSubset(StFTFont::Subset_Arabic)) {
27
+ aFont->changeFont(StFTFont::Subset_Arabic) = findCreate(aPack.Arabic.FamilyName, theSize);
28
+ }
29
+ if(aGenFont.isNull() || !aGenFont->hasSubset(StFTFont::Subset_MiscSymbols)) {
30
+ aFont->changeFont(StFTFont::Subset_MiscSymbols) = findCreate(aPack.MiscSymbols.FamilyName, theSize);
31
+ }
32
33
if(aGenFont.isNull()) {
34
aGenFont = findCreateFallback(theSize);
35
sview-17_04.tar.gz/StShared/StGLProjCamera.cpp -> sview-20_08.tar.gz/StShared/StGLProjCamera.cpp
Changed
134
1
2
StGLProjCamera::StGLProjCamera()
3
: myMatrix(),
4
myMatrixMono(),
5
+ myIsCustomFrust(false),
6
myFOVy(45.0f),
7
myZoom(1.0f),
8
myAspect(1.0f),
9
10
const GLfloat theZScreen)
11
: myMatrix(),
12
myMatrixMono(),
13
+ myIsCustomFrust(false),
14
myFOVy(theFOVy),
15
myZoom(1.0f),
16
myAspect(1.0f),
17
18
updateFrustum();
19
}
20
21
+StGLProjCamera::StGLProjCamera(const StGLProjCamera& theOther)
22
+: myMatrix(theOther.myMatrix),
23
+ myMatrixMono(theOther.myMatrixMono),
24
+ myVrFrustumL(theOther.myVrFrustumL),
25
+ myVrFrustumR(theOther.myVrFrustumR),
26
+ myIsCustomFrust(theOther.myIsCustomFrust),
27
+ myFOVy(theOther.myFOVy),
28
+ myZoom(theOther.myZoom),
29
+ myAspect(theOther.myAspect),
30
+ myZScreen(theOther.myZScreen),
31
+ myIOD(theOther.myIOD),
32
+ myFrustL(theOther.myFrustL),
33
+ myFrustR(theOther.myFrustR),
34
+ myFrustM(theOther.myFrustM),
35
+ myFrust(NULL),
36
+ myIsPersp(theOther.myIsPersp) {
37
+ myFrust = &myFrustM;
38
+ if(theOther.myFrust == &theOther.myFrustL) {
39
+ myFrust = &myFrustL;
40
+ } else if(theOther.myFrust == &theOther.myFrustR) {
41
+ myFrust = &myFrustR;
42
+ }
43
+ updateFrustum();
44
+}
45
+
46
+void StGLProjCamera::copyFrom(const StGLProjCamera& theOther) {
47
+ myMatrix = theOther.myMatrix;
48
+ myMatrixMono = theOther.myMatrixMono;
49
+ myVrFrustumL = theOther.myVrFrustumL;
50
+ myVrFrustumR = theOther.myVrFrustumR;
51
+ myIsCustomFrust = theOther.myIsCustomFrust;
52
+ myFOVy = theOther.myFOVy;
53
+ myZoom = theOther.myZoom;
54
+ myAspect = theOther.myAspect;
55
+ myZScreen = theOther.myZScreen;
56
+ myIOD = theOther.myIOD;
57
+ myFrustL = theOther.myFrustL;
58
+ myFrustR = theOther.myFrustR;
59
+ myFrustM = theOther.myFrustM;
60
+ myIsPersp = theOther.myIsPersp;
61
+
62
+ myFrust = &myFrustM;
63
+ if(theOther.myFrust == &theOther.myFrustL) {
64
+ myFrust = &myFrustL;
65
+ } else if(theOther.myFrust == &theOther.myFrustR) {
66
+ myFrust = &myFrustR;
67
+ }
68
+ updateFrustum();
69
+}
70
+
71
void StGLProjCamera::getZParams(const GLdouble theZValue,
72
StRectD_t& theSectRect) const {
73
if(myIsPersp) {
74
75
return std::atan2(aDYHalf, myFrustM.zNear * myZoom);
76
}
77
78
+void StGLProjCamera::resetCustomProjection() {
79
+ myVrFrustumL = StRectF_t();
80
+ myVrFrustumR = StRectF_t();
81
+ myIsCustomFrust = false;
82
+ updateFrustum();
83
+}
84
+
85
+void StGLProjCamera::setCustomProjection(const StRectF_t& theLeft, const StRectF_t& theRight) {
86
+ myVrFrustumL = theLeft;
87
+ myVrFrustumR = theRight;
88
+ myIsCustomFrust = true;
89
+ updateFrustum();
90
+}
91
+
92
void StGLProjCamera::updateFrustum() {
93
// sets top of frustum based on FOVy and near clipping plane
94
+ const GLfloat aZNear = myFrustM.zNear;
95
+ GLfloat aDXStereoShift = (0.5f * myIOD) * aZNear / myZScreen;
96
+
97
GLfloat aDYHalf = myIsPersp
98
- ? (myZoom * myFrustM.zNear * std::tan(ST_DTR_HALF * myFOVy))
99
- : (myZoom * myFrustM.zNear); ///
100
- // sets right of frustum based on aspect ratio
101
+ ? (myZoom * aZNear * std::tan(ST_DTR_HALF * myFOVy))
102
+ : (myZoom * aZNear);
103
GLfloat aDXHalf = myAspect * aDYHalf;
104
- GLfloat aDXStereoShift = (0.5f * myIOD) * myFrustM.zNear / myZScreen;
105
+ /*GLfloat aDXHalf = aDYHalf;
106
+ if(myAspect > 1.0f) {
107
+ aDXHalf *= myAspect;
108
+ } else {
109
+ aDYHalf /= myAspect;
110
+ }*/
111
112
// frustum for left view
113
myFrustL.yTop = aDYHalf;
114
115
myFrustM.xRight = aDXHalf;
116
myFrustM.xTranslation = 0.0f;
117
118
+ if(myIsCustomFrust) {
119
+ myFrustL.yTop = aZNear * myVrFrustumL.top();
120
+ myFrustL.yBottom = aZNear * myVrFrustumL.bottom();
121
+ myFrustL.xLeft = aZNear * myVrFrustumL.left();
122
+ myFrustL.xRight = aZNear * myVrFrustumL.right();
123
+
124
+ myFrustR.yTop = aZNear * myVrFrustumR.top();
125
+ myFrustR.yBottom = aZNear * myVrFrustumR.bottom();
126
+ myFrustR.xLeft = aZNear * myVrFrustumR.left();
127
+ myFrustR.xRight = aZNear * myVrFrustumR.right();
128
+ myFrustL.xTranslation = myFrustR.xTranslation = 0.0f;
129
+ }
130
+
131
// update current matrix
132
setupMatrix();
133
}
134
sview-17_04.tar.gz/StShared/StGLQuadTexture.cpp -> sview-20_08.tar.gz/StShared/StGLQuadTexture.cpp
Changed
123
1
2
/**
3
- * Copyright © 2009-2012 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2009-2020 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* Distributed under the Boost Software License, Version 1.0.
7
* See accompanying file license-boost.txt or copy at
8
9
: StGLTexture(GL_RGB8),
10
#endif
11
myDataSize(1.0f, 1.0f),
12
- myDisplayRatio(1.0f) {
13
+ myDisplayRatio(1.0f),
14
+ myPAR(1.0f),
15
+ myPanorama(StPanorama_OFF) {
16
//
17
}
18
19
20
const GLsizei theTextureSizeY) {
21
// test existing size / new size
22
/// TODO (Kirill Gavrilov#8) we can automatically reduce texture size here
23
- if((theTexture.getSizeX() < theTextureSizeX) ||
24
- (theTexture.getSizeY() < theTextureSizeY) ||
25
- !theTexture.isValid()) {
26
- ST_DEBUG_LOG("Requested texture size (" + theTextureSizeX + 'x' + theTextureSizeY
27
- + ") larger than current texture size(" + theTexture.getSizeX() + 'x' + theTexture.getSizeY() + ')');
28
- const GLsizei anOriginalSizeX = theTexture.getSizeX();
29
- const GLsizei anOriginalSizeY = theTexture.getSizeY();
30
-
31
- const GLint aMaxTexDim = theCtx.getMaxTextureSize();
32
- GLsizei aNewSizeX = stMin(theTextureSizeX, GLsizei(aMaxTexDim));
33
- GLsizei aNewSizeY = stMin(theTextureSizeY, GLsizei(aMaxTexDim));
34
- if(!theCtx.arbNPTW) {
35
- aNewSizeX = getPowerOfTwo(theTextureSizeX, GLsizei(aMaxTexDim));
36
- aNewSizeY = getPowerOfTwo(theTextureSizeY, GLsizei(aMaxTexDim));
37
+ if(theTexture.isValid()) {
38
+ if(theTexture.getSizeX() == theTextureSizeX
39
+ && theTexture.getSizeY() == theTextureSizeY) {
40
+ return;
41
}
42
- if((aNewSizeY != anOriginalSizeY)
43
- || (aNewSizeX != anOriginalSizeX)) {
44
- if(!theTexture.initTrash(theCtx, aNewSizeX, aNewSizeY)) {
45
- theTexture.initTrash(theCtx,
46
- (anOriginalSizeX > 0) ? anOriginalSizeX : 512,
47
- (anOriginalSizeY > 0) ? anOriginalSizeY : 512);
48
- ST_DEBUG_LOG("FAILED to Increase the texture size to (" + aNewSizeX + 'x' + aNewSizeY + ")!");
49
- } else {
50
- ST_DEBUG_LOG("Increase the texture size to (" + aNewSizeX + 'x' + aNewSizeY + ") success!");
51
- }
52
+
53
+ if(theTexture.getTarget() != GL_TEXTURE_CUBE_MAP
54
+ && theTexture.getSizeX() >= theTextureSizeX
55
+ && theTexture.getSizeY() >= theTextureSizeY) {
56
+ return;
57
+ }
58
+ }
59
+
60
+ ST_DEBUG_LOG("Requested texture size (" + theTextureSizeX + 'x' + theTextureSizeY
61
+ + ") larger than current texture size(" + theTexture.getSizeX() + 'x' + theTexture.getSizeY() + ')');
62
+ const GLsizei anOriginalSizeX = theTexture.getSizeX();
63
+ const GLsizei anOriginalSizeY = theTexture.getSizeY();
64
+
65
+ const GLint aMaxTexDim = theCtx.getMaxTextureSize();
66
+ GLsizei aNewSizeX = stMin(theTextureSizeX, GLsizei(aMaxTexDim));
67
+ GLsizei aNewSizeY = stMin(theTextureSizeY, GLsizei(aMaxTexDim));
68
+ if(!theCtx.arbNPTW) {
69
+ aNewSizeX = getPowerOfTwo(theTextureSizeX, GLsizei(aMaxTexDim));
70
+ aNewSizeY = getPowerOfTwo(theTextureSizeY, GLsizei(aMaxTexDim));
71
+ }
72
+ if((aNewSizeY != anOriginalSizeY)
73
+ || (aNewSizeX != anOriginalSizeX)) {
74
+ if(!theTexture.initTrash(theCtx, aNewSizeX, aNewSizeY)) {
75
+ theTexture.initTrash(theCtx,
76
+ (anOriginalSizeX > 0) ? anOriginalSizeX : 512,
77
+ (anOriginalSizeY > 0) ? anOriginalSizeY : 512);
78
+ ST_DEBUG_LOG("FAILED to Increase the texture size to (" + aNewSizeX + 'x' + aNewSizeY + ")!");
79
} else {
80
- ST_DEBUG_LOG("Not possible to Increase the texture size!");
81
+ ST_DEBUG_LOG("Increase the texture size to (" + aNewSizeX + 'x' + aNewSizeY + ") success!");
82
}
83
+ } else {
84
+ ST_DEBUG_LOG("Not possible to Increase the texture size!");
85
}
86
}
87
88
89
}
90
91
void StGLFrameTextures::setMinMagFilter(StGLContext& theCtx,
92
- const GLenum theMinMagFilter) {
93
- myTextures[0].setMinMagFilter(theCtx, theMinMagFilter);
94
+ const GLenum theMinFilter,
95
+ const GLenum theMagFilter) {
96
+ myTextures[0].setMinMagFilter(theCtx, theMinFilter, theMagFilter);
97
/// TODO (Kirill Gavrilov#4) investigate
98
- myTextures[1].setMinMagFilter(theCtx, GL_LINEAR);
99
- myTextures[2].setMinMagFilter(theCtx, GL_LINEAR);
100
- myTextures[3].setMinMagFilter(theCtx, GL_LINEAR);
101
+ const GLenum aMinFilter = theMinFilter != GL_NEAREST ? theMinFilter : GL_LINEAR;
102
+ const GLenum aMagFilter = theMagFilter != GL_NEAREST ? theMagFilter : GL_LINEAR;
103
+ myTextures[1].setMinMagFilter(theCtx, aMinFilter, aMagFilter);
104
+ myTextures[2].setMinMagFilter(theCtx, aMinFilter, aMagFilter);
105
+ myTextures[3].setMinMagFilter(theCtx, aMinFilter, aMagFilter);
106
}
107
108
void StGLQuadTexture::setMinMagFilter(StGLContext& theCtx,
109
- const GLenum theMinMagFilter) {
110
- myTextures[FRONT_TEXTURE + LEFT_TEXTURE].setMinMagFilter(theCtx, theMinMagFilter);
111
- myTextures[FRONT_TEXTURE + RIGHT_TEXTURE].setMinMagFilter(theCtx, theMinMagFilter);
112
- myTextures[BACK_TEXTURE + LEFT_TEXTURE].setMinMagFilter(theCtx, theMinMagFilter);
113
- myTextures[BACK_TEXTURE + RIGHT_TEXTURE].setMinMagFilter(theCtx, theMinMagFilter);
114
+ const GLenum theMinFilter,
115
+ const GLenum theMagFilter) {
116
+ myTextures[FRONT_TEXTURE + LEFT_TEXTURE].setMinMagFilter(theCtx, theMinFilter, theMagFilter);
117
+ myTextures[FRONT_TEXTURE + RIGHT_TEXTURE].setMinMagFilter(theCtx, theMinFilter, theMagFilter);
118
+ myTextures[BACK_TEXTURE + LEFT_TEXTURE].setMinMagFilter(theCtx, theMinFilter, theMagFilter);
119
+ myTextures[BACK_TEXTURE + RIGHT_TEXTURE].setMinMagFilter(theCtx, theMinFilter, theMagFilter);
120
}
121
122
StGLQuadTexture::StGLQuadTexture()
123
sview-17_04.tar.gz/StShared/StGLTextFormatter.cpp -> sview-20_08.tar.gz/StShared/StGLTextFormatter.cpp
Changed
127
1
2
/**
3
- * Copyright © 2012-2017 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2012-2018 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* Distributed under the Boost Software License, Version 1.0.
7
* See accompanying file license-boost.txt or copy at
8
9
10
#include <StGL/StGLVertexBuffer.h>
11
12
+#include <algorithm>
13
+
14
/**
15
* Auxiliary function to translate rectangles by the vector.
16
*/
17
18
}
19
}
20
21
+void StGLTextFormatter::flipLeftRight(size_t theCharFrom, size_t theCharTo) {
22
+ if(theCharFrom == theCharTo
23
+ || theCharTo == size_t(-1)) {
24
+ return;
25
+ }
26
+
27
+ float aRight = myRects[theCharTo].px.right();
28
+ for(size_t aCharIter = theCharFrom; aCharIter < theCharTo; ++aCharIter) {
29
+ StGLRect& aRect1 = myRects[aCharIter + 0].px;
30
+ const StGLRect& aRect2 = myRects[aCharIter + 1].px;
31
+ float aStepX = aRect2.left() - aRect1.left();
32
+ aRect1.moveRightTo(aRight);
33
+ aRight -= aStepX;
34
+ }
35
+
36
+ StGLRect& aRectLast = myRects[theCharTo].px;
37
+ aRectLast.moveRightTo(aRight);
38
+
39
+ std::reverse (myRects.begin() + theCharFrom, (theCharTo + 1) == myRects.size() ? myRects.end() : myRects.begin() + theCharTo + 1);
40
+}
41
+
42
void StGLTextFormatter::format(const GLfloat theWidth,
43
const GLfloat theHeight) {
44
if(myRectsNb == 0 || myIsFormatted) {
45
46
// split text into lines and apply horizontal alignment
47
myPenCurrLine = -myAscender;
48
size_t aRectIter = 0;
49
+ size_t aFlipLower = 0, aFlipInnerLower = 0;
50
+ bool isRight2Left = false, isLeft2RightInner = false;
51
for(StUtf8Iter anIter = myString.iterator(); *anIter != 0; ++anIter) {
52
const stUtf32_t aCharThis = *anIter;
53
if(aCharThis == '\x0D') {
54
55
myAlignWidth = myRects[aLastRect].px.right();
56
///toCorrectXAlignment = true;
57
}
58
+ if(isRight2Left) {
59
+ if(isLeft2RightInner) {
60
+ flipLeftRight(aFlipInnerLower, aLastRect);
61
+ isLeft2RightInner = false;
62
+ }
63
+ flipLeftRight(aFlipLower, aLastRect);
64
+ aFlipLower = aLastRect + 1;
65
+ }
66
newLine(aLastRect);
67
continue;
68
} else if(aCharThis == ' ') {
69
70
continue;
71
}
72
73
+ if(StFTFont::isRightToLeft(aCharThis)) {
74
+ if(!isRight2Left) {
75
+ isRight2Left = true;
76
+ aFlipLower = aRectIter;
77
+ } else if(isLeft2RightInner) {
78
+ flipLeftRight(aFlipInnerLower, aRectIter - 1);
79
+ isLeft2RightInner = false;
80
+ }
81
+ } else if(isRight2Left) {
82
+ if((aCharThis >= '0' && aCharThis <= '9')
83
+ || (isLeft2RightInner && (aCharThis == '.' || aCharThis == ','))) {
84
+ if(!isLeft2RightInner) {
85
+ isLeft2RightInner = true;
86
+ aFlipInnerLower = aRectIter;
87
+ }
88
+ } else {
89
+ isRight2Left = false;
90
+ flipLeftRight(aFlipLower, aRectIter - 1);
91
+ aFlipLower = aRectIter;
92
+ }
93
+ }
94
+
95
GLfloat aWidth = myRects[aRectIter].px.right() - myLineLeft;
96
myTextWidth = stMax(myTextWidth, aWidth);
97
if(theWidth > 0.0f && aWidth >= theWidth) {
98
99
aLastRect = aRectIter - 1;
100
}
101
102
+ if(isRight2Left) {
103
+ if(isLeft2RightInner) {
104
+ flipLeftRight(aFlipInnerLower, aLastRect);
105
+ isLeft2RightInner = false;
106
+ }
107
+ flipLeftRight(aFlipLower, aLastRect);
108
+ aFlipLower = aLastRect + 1;
109
+ }
110
newLine(aLastRect);
111
}
112
113
114
if(myRectsNb != 0) {
115
myTextWidth = stMax(myTextWidth, myRects[myRectsNb - 1].px.right() - myLineLeft);
116
}
117
+ if(isRight2Left) {
118
+ if(isLeft2RightInner) {
119
+ flipLeftRight(aFlipInnerLower, myRectsNb - 1);
120
+ isLeft2RightInner = false;
121
+ }
122
+ flipLeftRight(aFlipLower, myRectsNb - 1);
123
+ }
124
newLine(myRectsNb - 1);
125
if(myRectsNb != 0
126
&& myAlignWidth <= 0.0f) {
127
sview-17_04.tar.gz/StShared/StGLTexture.cpp -> sview-20_08.tar.gz/StShared/StGLTexture.cpp
Changed
502
1
2
/**
3
- * Copyright © 2009-2015 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2009-2019 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* Distributed under the Boost Software License, Version 1.0.
7
* See accompanying file license-boost.txt or copy at
8
9
#include <StImage/StImagePlane.h>
10
11
#include <StGLCore/StGLCore20.h>
12
+#include <StGL/StGLArbFbo.h>
13
#include <StGL/StGLContext.h>
14
15
#include <StStrings/StLogger.h>
16
#include <stAssert.h>
17
18
-bool StGLTexture::getInternalFormat(const StGLContext& theCtx,
19
- const StImagePlane& theData,
20
- GLint& theInternalFormat) {
21
- (void )theCtx;
22
- // sized formats are not supported by OpenGL ES
23
- switch(theData.getFormat()) {
24
+#ifndef GL_R16
25
+ #define GL_R16 0x822A
26
+ #define GL_R16F 0x822D
27
+ #define GL_R32F 0x822E
28
+ #define GL_RGB16F 0x881B
29
+ #define GL_RGBA32F 0x8814
30
+ #define GL_RGB32F 0x8815
31
+ #define GL_RGBA16F 0x881A
32
+ #define GL_RGB16F 0x881B
33
+ #define GL_RGB4 0x804F
34
+ #define GL_RGB5 0x8050
35
+ #define GL_RGB8 0x8051
36
+ #define GL_RGB10 0x8052
37
+ #define GL_RGB12 0x8053
38
+ #define GL_RGB16 0x8054
39
+ #define GL_RGBA8 0x8058
40
+ #define GL_RGB10_A2 0x8059
41
+ #define GL_RGBA12 0x805A
42
+ #define GL_RGBA16 0x805B
43
+ //#define GL_ALPHA4 0x803B
44
+ #define GL_ALPHA8 0x803C
45
+ #define GL_ALPHA16 0x803E
46
+
47
+ #define GL_HALF_FLOAT 0x140B
48
+ #define GL_UNSIGNED_INT_2_10_10_10_REV 0x8368
49
+#endif
50
+
51
+bool StGLTexture::getInternalFormat(const StGLContext& theCtx,
52
+ const StImagePlane::ImgFormat theFormat,
53
+ GLint& theInternalFormat) {
54
+ switch(theFormat) {
55
case StImagePlane::ImgRGBAF:
56
- case StImagePlane::ImgBGRAF:
57
- #if defined(GL_ES_VERSION_2_0)
58
- theInternalFormat = GL_RGBA;
59
- #else
60
+ case StImagePlane::ImgBGRAF: // BGRA requires texture swizzling on OpenGL ES
61
theInternalFormat = GL_RGBA32F;
62
- #endif
63
+ if(!theCtx.arbTexFloat) {
64
+ #if defined(GL_ES_VERSION_2_0)
65
+ return false;
66
+ #else
67
+ theInternalFormat = GL_RGBA8;
68
+ #endif
69
+ }
70
return true;
71
case StImagePlane::ImgRGBF:
72
- case StImagePlane::ImgBGRF:
73
- #if defined(GL_ES_VERSION_2_0)
74
- theInternalFormat = GL_RGB;
75
- #else
76
+ case StImagePlane::ImgBGRF: // BGR requires texture swizzling on OpenGL ES
77
theInternalFormat = GL_RGB32F;
78
- #endif
79
+ if(!theCtx.arbTexFloat) {
80
+ #if defined(GL_ES_VERSION_2_0)
81
+ return false;
82
+ #else
83
+ theInternalFormat = GL_RGB8;
84
+ #endif
85
+ }
86
return true;
87
case StImagePlane::ImgRGBA:
88
case StImagePlane::ImgBGRA:
89
#if defined(GL_ES_VERSION_2_0)
90
- theInternalFormat = GL_RGBA;
91
+ theInternalFormat = GL_RGBA; // non-sized for compatibility with OpenGL ES 2.0
92
#else
93
theInternalFormat = GL_RGBA8;
94
#endif
95
return true;
96
case StImagePlane::ImgRGBA64:
97
- #if defined(GL_ES_VERSION_2_0)
98
- theInternalFormat = GL_RGBA;
99
- #else
100
- theInternalFormat = GL_RGBA16;
101
- #endif
102
- return true;
103
+ theInternalFormat = theCtx.arbTexRG ? GL_RGBA16 : GL_RGBA8;
104
+ return theCtx.extTexR16;
105
case StImagePlane::ImgRGB: {
106
theInternalFormat = GL_RGB8;
107
return true;
108
109
case StImagePlane::ImgBGR: {
110
theInternalFormat = GL_RGB8;
111
#if defined(GL_ES_VERSION_2_0)
112
- return false;
113
+ return false; // still can be done via swizzling...
114
#else
115
return true;
116
#endif
117
}
118
case StImagePlane::ImgBGR32:
119
- #if defined(GL_ES_VERSION_2_0)
120
theInternalFormat = GL_RGB8;
121
- if(!theCtx.extTexBGRA8) {
122
- return false;
123
+ #if defined(GL_ES_VERSION_2_0)
124
+ if(theCtx.extTexBGRA8) {
125
+ // GL_EXT_texture_format_BGRA8888 has been introduced for OpenGL ES 1.0
126
+ // and does not defined sized format supported by OpenGL ES 3.0+
127
+ theInternalFormat = GL_BGRA_EXT;
128
+ } else {
129
+ return false; // still can be done via swizzling...
130
}
131
-
132
- // GL_EXT_texture_format_BGRA8888 has been introduced for OpenGL ES 1.0
133
- // and does not defined sized format supported by OpenGL ES 3.0+
134
- theInternalFormat = GL_BGRA_EXT;
135
- #else
136
- theInternalFormat = GL_RGB8;
137
#endif
138
return true;
139
case StImagePlane::ImgRGB48:
140
- #if defined(GL_ES_VERSION_2_0)
141
- theInternalFormat = GL_RGB;
142
- #else
143
theInternalFormat = GL_RGB16;
144
- #endif
145
- return true;
146
+ return theCtx.extTexR16;
147
case StImagePlane::ImgGrayF:
148
- #if defined(GL_ES_VERSION_2_0)
149
- theInternalFormat = GL_ALPHA;
150
- #else
151
- //theInternalFormat = GL_R32F; // OpenGL3+ hardware
152
- //theInternalFormat = GL_ALPHA32F_ARB;
153
- theInternalFormat = GL_ALPHA16; // backward compatibility
154
- #endif
155
+ theInternalFormat = GL_R32F;
156
+ if(!theCtx.arbTexFloat || !theCtx.arbTexRG) {
157
+ #if defined(GL_ES_VERSION_2_0)
158
+ return false;
159
+ #else
160
+ // there is also GL_ALPHA32F_ARB
161
+ theInternalFormat = theCtx.arbTexRG ? GL_R16 : GL_ALPHA16;
162
+ #endif
163
+ }
164
return true;
165
case StImagePlane::ImgGray16:
166
- #if defined(GL_ES_VERSION_2_0)
167
- theInternalFormat = GL_ALPHA;
168
- #else
169
- //theInternalFormat = GL_R16; // OpenGL3+ hardware
170
- theInternalFormat = GL_ALPHA16; // backward compatibility
171
+ theInternalFormat = GL_R16; // equals to GL_R16_EXT on OpenGL ES extension
172
+ #if !defined(GL_ES_VERSION_2_0)
173
+ theInternalFormat = theCtx.arbTexRG ? GL_R16 : GL_ALPHA16;
174
#endif
175
- return true;
176
+ return theCtx.extTexR16;
177
case StImagePlane::ImgGray:
178
#if defined(GL_ES_VERSION_2_0)
179
- theInternalFormat = GL_ALPHA;
180
+ theInternalFormat = theCtx.arbTexRG ? GL_R8 : GL_ALPHA;
181
#else
182
- // this texture format is deprecated with OpenGL3+, use GL_R8 (GL_RED) instead
183
- //theInternalFormat = GL_R8; // OpenGL3+ hardware
184
- theInternalFormat = GL_ALPHA8; // backward compatibility
185
+ theInternalFormat = theCtx.arbTexRG ? GL_R8 : GL_ALPHA8;
186
#endif
187
return true;
188
case StImagePlane::ImgUV:
189
- // this texture format is deprecated with OpenGL3+, use GL_R8 (GL_RED) instead
190
- //theInternalFormat = GL_RG8; // OpenGL3+ hardware
191
+ //theInternalFormat = theCtx.arbTexRG ? GL_RG8 : GL_LUMINANCE_ALPHA; // OpenGL3+
192
theInternalFormat = GL_LUMINANCE_ALPHA;
193
return true;
194
default:
195
196
const StImagePlane& theData,
197
GLenum& thePixelFormat,
198
GLenum& theDataType) {
199
-#if !defined(GL_ES_VERSION_2_0)
200
- (void )theCtx;
201
-#endif
202
thePixelFormat = GL_RGB;
203
theDataType = GL_UNSIGNED_BYTE;
204
switch(theData.getFormat()) {
205
case StImagePlane::ImgGray: {
206
- // we fill ALPHA channel in the texture!
207
- //thePixelFormat = GL_RED;
208
- thePixelFormat = GL_ALPHA;
209
+ thePixelFormat = theCtx.arbTexRG ? GL_RED : GL_ALPHA;
210
theDataType = GL_UNSIGNED_BYTE;
211
return true;
212
}
213
case StImagePlane::ImgGray16: {
214
- // we fill ALPHA channel in the texture!
215
- //thePixelFormat = GL_RED;
216
- thePixelFormat = GL_ALPHA;
217
+ thePixelFormat = theCtx.arbTexRG ? GL_RED : GL_ALPHA;
218
theDataType = GL_UNSIGNED_SHORT;
219
return true;
220
}
221
case StImagePlane::ImgUV: {
222
- //thePixelFormat = GL_RG;
223
+ //thePixelFormat = theCtx.arbTexRG ? GL_RG : GL_LUMINANCE_ALPHA;
224
thePixelFormat = GL_LUMINANCE_ALPHA;
225
theDataType = GL_UNSIGNED_BYTE;
226
return true;
227
228
return true;
229
}
230
case StImagePlane::ImgGrayF: {
231
- //thePixelFormat = GL_RED;
232
- thePixelFormat = GL_ALPHA;
233
+ thePixelFormat = theCtx.arbTexRG ? GL_RED : GL_ALPHA;
234
theDataType = GL_FLOAT;
235
return true;
236
}
237
238
}
239
}
240
241
-#ifndef GL_R16
242
- #define GL_R16 0x822A
243
- #define GL_R16F 0x822D
244
- #define GL_R32F 0x822E
245
- #define GL_RGB16F 0x881B
246
- #define GL_RGBA32F 0x8814
247
- #define GL_RGB32F 0x8815
248
- #define GL_RGBA16F 0x881A
249
- #define GL_RGB16F 0x881B
250
- #define GL_RGB4 0x804F
251
- #define GL_RGB5 0x8050
252
- #define GL_RGB8 0x8051
253
- #define GL_RGB10 0x8052
254
- #define GL_RGB12 0x8053
255
- #define GL_RGB16 0x8054
256
- #define GL_RGBA8 0x8058
257
- #define GL_RGB10_A2 0x8059
258
- #define GL_RGBA12 0x805A
259
- #define GL_RGBA16 0x805B
260
- //#define GL_ALPHA4 0x803B
261
- #define GL_ALPHA8 0x803C
262
- #define GL_ALPHA16 0x803E
263
-#endif
264
-
265
bool StGLTexture::isAlphaFormat(const GLint theInternalFormat) {
266
switch(theInternalFormat) {
267
// RED variations (GL_RED, OpenGL 3.0+)
268
269
}
270
}
271
272
+/**
273
+ * Return appropriate data type for specified internal format.
274
+ */
275
+static GLenum getDataType(GLint theInternalFormat) {
276
+ switch(theInternalFormat) {
277
+ case GL_RED:
278
+ case GL_R8:
279
+ case GL_RGB:
280
+ case GL_RGB8:
281
+ case GL_RGBA:
282
+ case GL_RGBA8:
283
+ case GL_BGRA_EXT:
284
+ case GL_ALPHA:
285
+ case GL_ALPHA8:
286
+ case GL_LUMINANCE:
287
+ case GL_LUMINANCE_ALPHA:
288
+ return GL_UNSIGNED_BYTE;
289
+ case GL_R16:
290
+ case GL_RGB16:
291
+ case GL_RGBA16:
292
+ case GL_ALPHA16:
293
+ return GL_UNSIGNED_SHORT;
294
+ case GL_R16F:
295
+ case GL_RGB16F:
296
+ case GL_RGBA16F:
297
+ return GL_HALF_FLOAT;
298
+ case GL_R32F:
299
+ case GL_RGB32F:
300
+ case GL_RGBA32F:
301
+ return GL_FLOAT;
302
+ /*case GL_RGB4:
303
+ case GL_RGB5:
304
+ case GL_RGB10:
305
+ case GL_RGB12:
306
+ case GL_RGBA12:
307
+ return GL_UNSIGNED_BYTE;*/
308
+ case GL_RGB10_A2:
309
+ return GL_UNSIGNED_INT_2_10_10_10_REV;
310
+ default:
311
+ return GL_UNSIGNED_BYTE;
312
+ }
313
+}
314
+
315
StGLTexture::StGLTexture()
316
: mySizeX(0),
317
mySizeY(0),
318
319
myTextFormat(GL_RGBA8),
320
myTextureId(NO_TEXTURE),
321
myTextureUnit(GL_TEXTURE0),
322
- myTextureFilt(GL_LINEAR) {
323
+ myFilterMin(GL_LINEAR),
324
+ myFilterMag(GL_LINEAR),
325
+ myHasMipMaps(0) {
326
//
327
}
328
329
330
myTextFormat(theTextureFormat),
331
myTextureId(NO_TEXTURE),
332
myTextureUnit(GL_TEXTURE0),
333
- myTextureFilt(GL_LINEAR) {
334
+ myFilterMin(GL_LINEAR),
335
+ myFilterMag(GL_LINEAR),
336
+ myHasMipMaps(0) {
337
//
338
}
339
340
341
theCtx.stglResetErrors();
342
#endif
343
344
+ myHasMipMaps = 0;
345
if(!isValid()) {
346
theCtx.core20fwd->glGenTextures(1, &myTextureId); // Create The Texture
347
}
348
bind(theCtx);
349
350
// texture interpolation parameters - could be overridden later
351
- theCtx.core20fwd->glTexParameteri(myTarget, GL_TEXTURE_MAG_FILTER, myTextureFilt);
352
- theCtx.core20fwd->glTexParameteri(myTarget, GL_TEXTURE_MIN_FILTER, myTextureFilt);
353
+ theCtx.core20fwd->glTexParameteri(myTarget, GL_TEXTURE_MIN_FILTER, myFilterMin);
354
+ theCtx.core20fwd->glTexParameteri(myTarget, GL_TEXTURE_MAG_FILTER, myFilterMag);
355
theCtx.core20fwd->glTexParameteri(myTarget, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
356
theCtx.core20fwd->glTexParameteri(myTarget, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
357
358
359
return false;
360
}
361
362
+ // NULL is passed to glTexImage2D(), so that there is no actual data to be interpreted.
363
+ // However, OpenGL ES raises GL_INVALID_OPERATION if invalid type is passed.
364
+ const GLenum aDataType = getDataType(myTextFormat);
365
GLint anInternalFormat = myTextFormat;
366
#if defined(GL_ES_VERSION_2_0)
367
- if(!theCtx.isGlGreaterEqual(3, 0)) {
368
+ if(!theCtx.isGlGreaterEqual(3, 0) && aDataType == GL_UNSIGNED_BYTE) {
369
// sized formats are not supported here
370
anInternalFormat = theDataFormat;
371
}
372
373
for(int aTargetIter = 0; aTargetIter < 6; ++aTargetIter) {
374
theCtx.core20fwd->glTexImage2D(aTargets[aTargetIter], 0, anInternalFormat,
375
mySizeX, mySizeY, 0,
376
- theDataFormat, GL_UNSIGNED_BYTE, theData);
377
+ theDataFormat, aDataType, theData);
378
}
379
} else {
380
theCtx.core20fwd->glTexImage2D(myTarget, 0, anInternalFormat,
381
mySizeX, mySizeY, 0,
382
- theDataFormat, GL_UNSIGNED_BYTE, theData);
383
+ theDataFormat, aDataType, theData);
384
}
385
#if defined(GL_ES_VERSION_2_0)
386
// proxy texture is unavailable - check for errors
387
388
}
389
390
void StGLTexture::setMinMagFilter(StGLContext& theCtx,
391
- const GLenum theMinMagFilter) {
392
- if(!isValid()) {
393
- myTextureFilt = theMinMagFilter;
394
+ const GLenum theMinFilter,
395
+ const GLenum theMagFilter) {
396
+ const bool needsMipMaps = theMinFilter != GL_NEAREST
397
+ && theMinFilter != GL_LINEAR;
398
+ if(myFilterMin == theMinFilter
399
+ && myFilterMag == theMagFilter
400
+ && (!needsMipMaps || myHasMipMaps != 0)) {
401
return;
402
- } else if(myTextureFilt == theMinMagFilter) {
403
+ }
404
+
405
+ myFilterMin = theMinFilter;
406
+ myFilterMag = theMagFilter;
407
+ if(!isValid()) {
408
return;
409
}
410
- myTextureFilt = theMinMagFilter;
411
+
412
bind(theCtx);
413
- theCtx.core20fwd->glTexParameteri(myTarget, GL_TEXTURE_MAG_FILTER, myTextureFilt);
414
- theCtx.core20fwd->glTexParameteri(myTarget, GL_TEXTURE_MIN_FILTER, myTextureFilt);
415
+ if(needsMipMaps && myHasMipMaps == 0) {
416
+ theCtx.arbFbo->glGenerateMipmap(myTarget);
417
+ const GLenum anErr = glGetError();
418
+ if(anErr != GL_NO_ERROR) {
419
+ // note that OpenGL ES 2.0 does not support mip-map generation of non-power-of-two textures
420
+ ST_ERROR_LOG("Failed to generate mipmap levels with error " + theCtx.stglErrorToString(anErr));
421
+ myHasMipMaps = -1;
422
+ } else {
423
+ myHasMipMaps = 1;
424
+ }
425
+ }
426
+ GLenum aMinFilter = !needsMipMaps || myHasMipMaps == 1
427
+ ? myFilterMin
428
+ : GL_LINEAR;
429
+ theCtx.core20fwd->glTexParameteri(myTarget, GL_TEXTURE_MIN_FILTER, aMinFilter);
430
+ theCtx.core20fwd->glTexParameteri(myTarget, GL_TEXTURE_MAG_FILTER, myFilterMag);
431
+
432
unbind(theCtx);
433
}
434
435
436
437
bool StGLTexture::fillPatch(StGLContext& theCtx,
438
const StImagePlane& theData,
439
+ const GLenum theTarget,
440
+ const GLsizei theRowFrom,
441
+ const GLsizei theRowTo) {
442
+#ifdef __ANDROID__
443
+ GLsizei aBatchRows = 0;
444
+#else
445
+ GLsizei aBatchRows = 128; // TODO does it makes sense nowadays?
446
+#endif
447
+ return fillPatch(theCtx, theData, theTarget, theRowFrom, theRowTo, aBatchRows);
448
+}
449
+
450
+bool StGLTexture::fillPatch(StGLContext& theCtx,
451
+ const StImagePlane& theData,
452
GLenum theTarget,
453
const GLsizei theRowFrom,
454
const GLsizei theRowTo,
455
456
if(theData.isNull() || !isValid()) {
457
return false;
458
}
459
+
460
GLenum aPixelFormat, aDataType;
461
if(!getDataFormat(theCtx, theData, aPixelFormat, aDataType)) {
462
return false;
463
464
return false;
465
}
466
467
+ myHasMipMaps = 0;
468
bind(theCtx);
469
470
// setup the alignment
471
472
toBatchCopy = false;
473
}
474
475
- if(!theCtx.hasUnpack
476
+ if(!theCtx.getDeviceCaps().hasUnpack
477
&& anExtraBytes >= anAligment) {
478
toBatchCopy = false;
479
}
480
481
if(toBatchCopy) {
482
- if(theCtx.hasUnpack) {
483
+ if(theCtx.getDeviceCaps().hasUnpack) {
484
theCtx.core20fwd->glPixelStorei(GL_UNPACK_ROW_LENGTH, GLint(aPixelsWidth));
485
}
486
487
488
theData.getData(aRow, 0));
489
}
490
491
- if(theCtx.hasUnpack) {
492
+ if(theCtx.getDeviceCaps().hasUnpack) {
493
theCtx.core20fwd->glPixelStorei(GL_UNPACK_ROW_LENGTH, 0);
494
}
495
} else {
496
// copy row by row copy (the image plane greater than texture or batch copy is impossible)
497
- if(theCtx.hasUnpack) {
498
+ if(theCtx.getDeviceCaps().hasUnpack) {
499
theCtx.core20fwd->glPixelStorei(GL_UNPACK_ROW_LENGTH, 0);
500
}
501
502
sview-17_04.tar.gz/StShared/StGLTextureData.cpp -> sview-20_08.tar.gz/StShared/StGLTextureData.cpp
Changed
347
1
2
/**
3
- * Copyright © 2009-2015 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2009-2020 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* Distributed under the Boost Software License, Version 1.0.
7
* See accompanying file license-boost.txt or copy at
8
9
#include <StStrings/StLogger.h>
10
11
#include <StGLCore/StGLCore11.h>
12
+#include <StGL/StGLContext.h>
13
14
-StGLTextureData::StGLTextureData()
15
+#include <StAV/StAVImage.h>
16
+
17
+StGLTextureData::StGLTextureData(const StHandle<StGLTextureUploadParams>& theUploadParams)
18
: myPrev(NULL),
19
myNext(NULL),
20
myDataPtr(NULL),
21
22
myPts(0.0),
23
mySrcFormat(StFormat_AUTO),
24
myCubemapFormat(StCubemap_OFF),
25
+ myUploadParams(theUploadParams),
26
myFillFromRow(0),
27
myFillRows(0) {
28
//
29
30
theCoeffX = 6;
31
theCoeffY = 1;
32
return true;
33
+ } else if(thePlane.getSizeY() / 6 == thePlane.getSizeX()) {
34
+ theCoeffX = 1;
35
+ theCoeffY = 6;
36
+ return true;
37
} else if(thePlane.getSizeX() / 3 == thePlane.getSizeY() / 2) {
38
theCoeffX = 3;
39
theCoeffY = 2;
40
return true;
41
+ } else if(thePlane.getSizeX() / 2 == thePlane.getSizeY() / 3) {
42
+ theCoeffX = 2;
43
+ theCoeffY = 3;
44
+ return true;
45
}
46
return false;
47
}
48
49
}
50
51
void StGLTextureData::validateCubemap(const StCubemap theCubemap) {
52
- if(theCubemap != StCubemap_Packed) {
53
+ if(theCubemap != StCubemap_Packed
54
+ && theCubemap != StCubemap_PackedEAC) {
55
myCubemapFormat = StCubemap_OFF;
56
return;
57
}
58
59
myCubemapFormat = theCubemap;
60
+ if(theCubemap == StCubemap_PackedEAC) {
61
+ return;
62
+ }
63
+
64
size_t aCoeffs[2] = {0, 0};
65
if(!myDataL.isNull()) {
66
for(size_t aPlaneId = 0; aPlaneId < 4; ++aPlaneId) {
67
68
return;
69
}
70
71
- if(myCubemapFormat != StCubemap_Packed) {
72
+ if(myCubemapFormat != StCubemap_Packed
73
+ && myCubemapFormat != StCubemap_PackedEAC) {
74
theFrameTexture.fillPatch(theCtx, theData, GL_TEXTURE_2D, myFillFromRow, myFillFromRow + myFillRows);
75
return;
76
}
77
78
size_t aCoeffs[2] = {0, 0};
79
- if(!checkCubeMap(theData, aCoeffs[0], aCoeffs[1])) {
80
- return;
81
+ if(myCubemapFormat == StCubemap_PackedEAC) {
82
+ if(theData.getSizeX() > theData.getSizeY()) {
83
+ aCoeffs[0] = 3;
84
+ aCoeffs[1] = 2;
85
+ } else {
86
+ aCoeffs[0] = 2;
87
+ aCoeffs[1] = 3;
88
+ }
89
+ } else {
90
+ if(!checkCubeMap(theData, aCoeffs[0], aCoeffs[1])) {
91
+ return;
92
+ }
93
}
94
95
- const size_t aPatch = theData.getSizeX() / aCoeffs[0];
96
- if(aPatch < 2) {
97
+ const size_t aPatchX = theData.getSizeX() / aCoeffs[0];
98
+ const size_t aPatchY = theData.getSizeY() / aCoeffs[1];
99
+ if(aPatchX < 2 || aPatchY < 2) {
100
return;
101
}
102
103
- const GLenum aTargets[6] = { GL_TEXTURE_CUBE_MAP_POSITIVE_X,
104
- GL_TEXTURE_CUBE_MAP_NEGATIVE_X,
105
- GL_TEXTURE_CUBE_MAP_POSITIVE_Y,
106
- GL_TEXTURE_CUBE_MAP_NEGATIVE_Y,
107
- GL_TEXTURE_CUBE_MAP_POSITIVE_Z,
108
- GL_TEXTURE_CUBE_MAP_NEGATIVE_Z };
109
+ static const GLenum THE_SIDES_GL[6] = { GL_TEXTURE_CUBE_MAP_POSITIVE_X, GL_TEXTURE_CUBE_MAP_NEGATIVE_X,
110
+ GL_TEXTURE_CUBE_MAP_POSITIVE_Y, GL_TEXTURE_CUBE_MAP_NEGATIVE_Y,
111
+ GL_TEXTURE_CUBE_MAP_POSITIVE_Z, GL_TEXTURE_CUBE_MAP_NEGATIVE_Z };
112
+ static const GLenum THE_SIDES_EAC32[6] = { GL_TEXTURE_CUBE_MAP_POSITIVE_X, GL_TEXTURE_CUBE_MAP_NEGATIVE_Z, GL_TEXTURE_CUBE_MAP_NEGATIVE_X,
113
+ GL_TEXTURE_CUBE_MAP_NEGATIVE_Y, GL_TEXTURE_CUBE_MAP_POSITIVE_Z, GL_TEXTURE_CUBE_MAP_POSITIVE_Y };
114
+ static const GLenum THE_SIDES_EAC23[6] = { GL_TEXTURE_CUBE_MAP_NEGATIVE_X, GL_TEXTURE_CUBE_MAP_POSITIVE_Y,
115
+ GL_TEXTURE_CUBE_MAP_NEGATIVE_Z, GL_TEXTURE_CUBE_MAP_POSITIVE_Z,
116
+ GL_TEXTURE_CUBE_MAP_POSITIVE_X, GL_TEXTURE_CUBE_MAP_NEGATIVE_Y };
117
+
118
+ const GLenum* aTargets = myCubemapFormat == StCubemap_PackedEAC
119
+ ? (aCoeffs[1] == 3 ? THE_SIDES_EAC23 : THE_SIDES_EAC32)
120
+ : THE_SIDES_GL;
121
for(size_t aTargetIter = 0; aTargetIter < 6; ++aTargetIter) {
122
StImagePlane aPlane;
123
- const bool isSecondRow = (aCoeffs[1] == 2 && aTargetIter >= 3);
124
- const size_t aLeft = isSecondRow ? (aPatch * (aTargetIter - 3)) : (aPatch * aTargetIter);
125
- const size_t aTop = isSecondRow ? aPatch : 0;
126
+ size_t aTop = 0, aLeft = 0;
127
+ bool toTranspose = false;
128
+ switch(aCoeffs[1]) {
129
+ case 1: { // 6x1
130
+ aLeft = aPatchX * aTargetIter;
131
+ aTop = 0;
132
+ break;
133
+ }
134
+ case 2: { // 3x2
135
+ if(aTargetIter >= 3) {
136
+ // second row
137
+ aLeft = aPatchX * (aTargetIter - 3);
138
+ aTop = aPatchY;
139
+ if(myCubemapFormat == StCubemap_PackedEAC) {
140
+ toTranspose = true;
141
+ }
142
+ } else {
143
+ // first row
144
+ aLeft = aPatchX * aTargetIter;
145
+ aTop = 0;
146
+ }
147
+ break;
148
+ }
149
+ case 3: { // 2x3
150
+ if(aTargetIter >= 4) {
151
+ // third row
152
+ aLeft = aPatchX * (aTargetIter - 4);
153
+ aTop = aPatchY * 2;
154
+ } else if(aTargetIter >= 2) {
155
+ // second row
156
+ aLeft = aPatchX * (aTargetIter - 2);
157
+ aTop = aPatchY;
158
+ } else {
159
+ // first row
160
+ aLeft = aPatchX * aTargetIter;
161
+ aTop = 0;
162
+ }
163
+
164
+ if(myCubemapFormat == StCubemap_PackedEAC
165
+ && (aTargetIter % 2) == 0) {
166
+ toTranspose = true;
167
+ }
168
+ break;
169
+ }
170
+ case 6: { // 1x6
171
+ aLeft = 0;
172
+ aTop = aPatchY * aTargetIter;
173
+ break;
174
+ }
175
+ }
176
if(!aPlane.initWrapper(theData.getFormat(), const_cast<GLubyte* >(theData.getData(aTop, aLeft)),
177
- aPatch, aPatch, theData.getSizeRowBytes())) {
178
+ aPatchX, aPatchY, theData.getSizeRowBytes())) {
179
ST_DEBUG_LOG("StGLTextureData::fillTexture(). wrapping failure");
180
continue;
181
}
182
- theFrameTexture.fillPatch(theCtx, aPlane, aTargets[aTargetIter], myFillFromRow, myFillFromRow + myFillRows);
183
+
184
+ StImagePlane* aResPlane = &aPlane;
185
+
186
+ // this is too slow without multi-threading
187
+ (void )toTranspose;
188
+ /*if(toTranspose) {
189
+ StImagePlane& aTmpPlane = theCtx.getTmpImagePlane1();
190
+ aTmpPlane.initTransposedCopy(aPlane, aCoeffs[1] != 3);
191
+ aResPlane = &aTmpPlane;
192
+ }
193
+
194
+ if(aPatchX != aPatchY) {
195
+ size_t aPatch = stMax(aPatchX, aPatchY);
196
+ StImagePlane& aTmpPlane2 = theCtx.getTmpImagePlane2();
197
+ if(aTmpPlane2.getFormat() != aResPlane->getFormat()
198
+ || aTmpPlane2.getSizeX() != aResPlane->getSizeX()
199
+ || aTmpPlane2.getSizeY() != aResPlane->getSizeY()) {
200
+ aTmpPlane2.initTrash(aResPlane->getFormat(), aPatch, aPatch);
201
+ }
202
+ if(!aTmpPlane2.isNull()) {
203
+ StAVImage::resizePlane(*aResPlane, aTmpPlane2);
204
+ aResPlane = &aTmpPlane2;
205
+ }
206
+ }*/
207
+
208
+ theFrameTexture.fillPatch(theCtx, *aResPlane, aTargets[aTargetIter], myFillFromRow, myFillFromRow + myFillRows);
209
}
210
}
211
212
-static void setupDataRectangle(const StImagePlane& theImagePlane,
213
- const GLfloat thePixelRatio,
214
- StGLFrameTexture& theTextureFrame) {
215
+void StGLTextureData::setupDataRectangle(const StImagePlane& theImagePlane,
216
+ const GLfloat thePixelRatio,
217
+ StGLFrameTexture& theTextureFrame) {
218
if(theImagePlane.isNull() || !theTextureFrame.isValid()) {
219
return;
220
}
221
222
- const GLfloat aSizeXFloat = stMin(GLfloat(theImagePlane.getSizeX()), GLfloat(theTextureFrame.getSizeX()));
223
- const GLfloat aSizeYFloat = stMin(GLfloat(theImagePlane.getSizeY()), GLfloat(theTextureFrame.getSizeY()));
224
+ size_t anImgSizeX = theImagePlane.getSizeX();
225
+ size_t anImgSizeY = theImagePlane.getSizeY();
226
+
227
+ StPanorama aPano = StPanorama_OFF;
228
+ size_t aCoeffs[2] = {0, 0};
229
+ if(myCubemapFormat == StCubemap_Packed
230
+ && checkCubeMap(theImagePlane, aCoeffs[0], aCoeffs[1])) {
231
+ anImgSizeX = anImgSizeX / aCoeffs[0];
232
+ anImgSizeY = anImgSizeY / aCoeffs[1];
233
+ switch(aCoeffs[0]) {
234
+ case 1: aPano = StPanorama_Cubemap1_6; break;
235
+ case 3: aPano = StPanorama_Cubemap3_2; break;
236
+ case 6: aPano = StPanorama_Cubemap6_1; break;
237
+ }
238
+ } else if(myCubemapFormat == StCubemap_PackedEAC) {
239
+ if(theImagePlane.getSizeX() > theImagePlane.getSizeY()) {
240
+ aCoeffs[0] = 3;
241
+ aCoeffs[1] = 2;
242
+ aPano = StPanorama_Cubemap3_2ytb;
243
+ } else {
244
+ aCoeffs[0] = 2;
245
+ aCoeffs[1] = 3;
246
+ aPano = StPanorama_Cubemap2_3ytb;
247
+ }
248
+ anImgSizeX = anImgSizeX / aCoeffs[0];
249
+ anImgSizeY = anImgSizeY / aCoeffs[1];
250
+ }
251
+
252
+ const GLfloat aSizeXFloat = stMin(GLfloat(anImgSizeX), GLfloat(theTextureFrame.getSizeX()));
253
+ const GLfloat aSizeYFloat = stMin(GLfloat(anImgSizeY), GLfloat(theTextureFrame.getSizeY()));
254
StGLVec2 aDataSize (aSizeXFloat / GLfloat(theTextureFrame.getSizeX()),
255
aSizeYFloat / GLfloat(theTextureFrame.getSizeY()));
256
if(aDataSize.x() > 1.0f) {
257
258
}
259
theTextureFrame.setDataSize(aDataSize);
260
theTextureFrame.setDisplayRatio((thePixelRatio * aSizeXFloat) / aSizeYFloat);
261
+ theTextureFrame.setPixelRatio(thePixelRatio);
262
+ theTextureFrame.setPackedPanorama(aPano);
263
}
264
265
void StGLTextureData::setupAttributes(StGLFrameTextures& stFrameTextures, const StImage& theImage) {
266
267
continue;
268
}
269
270
- if(!StGLTexture::getInternalFormat(theCtx, anImgPlane, anInternalFormat)) {
271
+ if(!StGLTexture::getInternalFormat(theCtx, anImgPlane.getFormat(), anInternalFormat)) {
272
aTexture.release(theCtx);
273
continue;
274
}
275
276
aTarget = GL_TEXTURE_CUBE_MAP;
277
aSizeX = aSizeX / GLsizei(aCoeffs[0]);
278
aSizeY = aSizeY / GLsizei(aCoeffs[1]);
279
+ if(aSizeX < 1) {
280
+ aTexture.release(theCtx);
281
+ continue;
282
+ }
283
+ aSizeX = stMax(aSizeX, aSizeY); // cubemap requires squared images
284
+ aSizeY = stMax(aSizeX, aSizeY);
285
+ } else if(theCubemap == StCubemap_PackedEAC) {
286
+ if(aSizeX > aSizeY) {
287
+ aSizeX /= 3;
288
+ aSizeY /= 2;
289
+ } else {
290
+ aSizeX /= 2;
291
+ aSizeY /= 3;
292
+ }
293
+ aTarget = GL_TEXTURE_CUBE_MAP;
294
+ aSizeX = stMax(aSizeX, aSizeY); // cubemap requires squared images
295
+ aSizeY = stMax(aSizeX, aSizeY);
296
}
297
if(aSizeX < 1) {
298
aTexture.release(theCtx);
299
300
theQTexture.getBack(StGLQuadTexture::LEFT_TEXTURE).setSource(StHandle<StStereoParams>());
301
theQTexture.getBack(StGLQuadTexture::RIGHT_TEXTURE).setSource(StHandle<StStereoParams>());
302
303
- // TODO (Kirill Gavrilov#9) this value is meanfull only for PageFlip,
304
- // also rows number may be replaced with bytes count
305
- static const GLsizei UPDATED_ROWS_MAX = 1088; // we use optimal value to update 1080p video frame at-once
306
- GLsizei maxRows = stMin(GLsizei(myDataL.getSizeY()), theQTexture.getBack(StGLQuadTexture::LEFT_TEXTURE).getSizeY());
307
- GLsizei iterations = (maxRows / (UPDATED_ROWS_MAX * 2)) + 1;
308
- if(!myDataR.isNull()) {
309
- maxRows = stMax(maxRows, stMin(GLsizei(myDataR.getSizeY()), theQTexture.getBack(StGLQuadTexture::RIGHT_TEXTURE).getSizeY()));
310
- iterations = maxRows / UPDATED_ROWS_MAX + 1;
311
+ const int aNbRowsL = stMin(int(myDataL.getSizeY()), theQTexture.getBack(StGLQuadTexture::LEFT_TEXTURE).getSizeY());
312
+ const int aNbRowsR = !myDataR.isNull()
313
+ ? stMin(int(myDataR.getSizeY()), theQTexture.getBack(StGLQuadTexture::RIGHT_TEXTURE).getSizeY())
314
+ : 0;
315
+ const int aNbMaxRows = stMax(aNbRowsL, aNbRowsR);
316
+
317
+ const int aMaxUploadChunkMiB = myUploadParams->MaxUploadChunkMiB;
318
+ const int aMaxUploadIterations = myUploadParams->MaxUploadIterations;
319
+ int aNbIters = 1;
320
+ if(aMaxUploadChunkMiB > 0 && aMaxUploadIterations > 1) {
321
+ size_t aStride = 0;
322
+ for(int aPlaneIter = 0; aPlaneIter < 4; ++aPlaneIter) {
323
+ const StImagePlane& aPlaneL = myDataL.getPlane(aPlaneIter);
324
+ if(!aPlaneL.isNull()) {
325
+ // don't use aPlane.getSizeRowBytes() here since it may contain extra padding for side-by-side input
326
+ aStride += aPlaneL.getSizeX() * aPlaneL.getSizePixelBytes();
327
+ }
328
+ if(!myDataR.isNull()) {
329
+ const StImagePlane& aPlaneR = myDataR.getPlane(aPlaneIter);
330
+ if(!aPlaneR.isNull()) {
331
+ aStride += aPlaneR.getSizeX() * aPlaneR.getSizePixelBytes();
332
+ }
333
+ }
334
+ }
335
+
336
+ const int aNbMaxFrameRows = int((size_t(aMaxUploadChunkMiB) * 1024 * 1024) / aStride);
337
+ aNbIters = stMin(aMaxUploadIterations, aNbMaxRows / aNbMaxFrameRows);
338
+ }
339
+ myFillRows = (aNbIters > 0) ? (aNbMaxRows / aNbIters) : aNbMaxRows;
340
+ if(myCubemapFormat == StCubemap_Packed || myCubemapFormat == StCubemap_PackedEAC) {
341
+ myFillRows = INT_MAX; /// TODO handle cube maps incremental updates specificall
342
}
343
- myFillRows = maxRows / iterations;
344
myFillFromRow = 0;
345
}
346
347
sview-17_04.tar.gz/StShared/StGLTextureQueue.cpp -> sview-20_08.tar.gz/StShared/StGLTextureQueue.cpp
Changed
51
1
2
myIsInUpdTexture(false),
3
myIsReadyToSwap(false),
4
myToCompress(false),
5
- myHasStream(false) {
6
+ myHasStream(false),
7
+ myUploadParams(new StGLTextureUploadParams()) {
8
ST_ASSERT(myQueueSizeMax >= 2, "StGLTextureQueue() - queue size limit should be >= 2");
9
+ // 1920x1080@YUV420p ~ 3 MiB
10
+ // 1920x1080@RGB8 ~ 6 MiB
11
+ // 3840x2160@YUV420p ~ 12 MiB
12
+ // 3840x2160@RGB8 ~ 24 MiB
13
+ // 3840x2160@YUV420p16 ~ 24 MiB
14
+ myUploadParams->MaxUploadChunkMiB = 6;
15
+ myUploadParams->MaxUploadIterations = 1;
16
17
// we create 'empty' queue
18
- myDataFront = new StGLTextureData();
19
+ myDataFront = new StGLTextureData(myUploadParams);
20
StGLTextureData* iter = myDataFront;
21
for(size_t i = 1; i < myQueueSizeMax; ++i) {
22
- iter->setNext(new StGLTextureData());
23
+ iter->setNext(new StGLTextureData(myUploadParams));
24
iter = iter->getNext();
25
}
26
iter->setNext(myDataFront); // data in loop
27
28
myMutexPop.unlock();
29
}
30
31
-void StGLTextureQueue::drop(const size_t theCount) {
32
+void StGLTextureQueue::drop(const size_t theCount,
33
+ double& thePtsFront) {
34
myMutexPop.lock();
35
myMutexPush.lock();
36
myMutexSize.lock();
37
if(myQueueSize < 2) {
38
- // to small queue
39
+ // too small queue
40
myMutexSize.unlock();
41
myMutexPush.unlock();
42
myMutexPop.unlock();
43
44
for(size_t i = 0; i < decr; ++i, myDataFront = myDataFront->getNext()) {
45
myDataFront->resetStParams();
46
}
47
+ thePtsFront = myDataFront->getPTS();
48
// reset queue
49
myQueueSize -= decr;
50
// empty texture update sequence
51
sview-20_08.tar.gz/StShared/StGLUVCylinder.cpp
Added
77
1
2
+/**
3
+ * Copyright © 2019-2020 Kirill Gavrilov <kirill@sview.ru>
4
+ *
5
+ * Distributed under the Boost Software License, Version 1.0.
6
+ * See accompanying file license-boost.txt or copy at
7
+ * http://www.boost.org/LICENSE_1_0.txt
8
+ */
9
+
10
+#include <StGLMesh/StGLUVCylinder.h>
11
+
12
+#include <StGLCore/StGLCore20.h>
13
+#include <StGL/StGLContext.h>
14
+
15
+StGLUVCylinder::StGLUVCylinder(const StGLVec3& theCenter,
16
+ const float theHeight,
17
+ const float theRadius,
18
+ const int theRings)
19
+: StGLMesh(GL_TRIANGLE_STRIP),
20
+ myCenter(theCenter),
21
+ myRadius(theRadius),
22
+ myHeight(theHeight),
23
+ myAngleFrom(0.0f),
24
+ myAngleTo(float(M_PI * 2.0)),
25
+ myNbRings(theRings) {
26
+ //
27
+}
28
+
29
+StGLUVCylinder::StGLUVCylinder(const StGLVec3& theCenter,
30
+ const float theHeight,
31
+ const float theRadius,
32
+ const float theAngleFrom,
33
+ const float theAngleTo,
34
+ const int theRings)
35
+: StGLMesh(GL_TRIANGLE_STRIP),
36
+ myCenter(theCenter),
37
+ myRadius(theRadius),
38
+ myHeight(theHeight),
39
+ myAngleFrom(theAngleFrom),
40
+ myAngleTo(theAngleTo),
41
+ myNbRings(theRings) {
42
+ //
43
+}
44
+
45
+
46
+StGLUVCylinder::~StGLUVCylinder() {
47
+ //
48
+}
49
+
50
+bool StGLUVCylinder::computeMesh() {
51
+ clearRAM();
52
+ if(myNbRings == 0) {
53
+ return false;
54
+ }
55
+
56
+ const int aNbVerts = (myNbRings + 1) * 2;
57
+ myVertices.initArray(aNbVerts);
58
+ myNormals .initArray(aNbVerts);
59
+ myTCoords .initArray(aNbVerts);
60
+
61
+ const float anAngle = myAngleTo - myAngleFrom;
62
+ for(int aRingIter = 0; aRingIter <= myNbRings; ++aRingIter) {
63
+ const float aPhi = myAngleFrom + float(aRingIter) * anAngle / float(myNbRings);
64
+ const float aTexCrd = float(aRingIter) / float(myNbRings);
65
+ myTCoords.changeValue(aRingIter * 2 + 0) = StGLVec2(aTexCrd, 0.0f);
66
+ myTCoords.changeValue(aRingIter * 2 + 1) = StGLVec2(aTexCrd, 1.0f);
67
+
68
+ const StGLVec3 aNorm(cosf(aPhi), 0.0f, sinf(aPhi));
69
+ myNormals.changeValue(aRingIter * 2 + 0) = aNorm;
70
+ myNormals.changeValue(aRingIter * 2 + 1) = aNorm;
71
+
72
+ myVertices.changeValue(aRingIter * 2 + 0) = myCenter + aNorm * myRadius - StGLVec3(0.0f, myHeight * 0.5f, 0.0f);
73
+ myVertices.changeValue(aRingIter * 2 + 1) = myCenter + aNorm * myRadius + StGLVec3(0.0f, myHeight * 0.5f, 0.0f);
74
+ }
75
+ return true;
76
+}
77
sview-17_04.tar.gz/StShared/StGLUVSphere.cpp -> sview-20_08.tar.gz/StShared/StGLUVSphere.cpp
Changed
59
1
2
/**
3
- * Copyright © 2010-2012 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2010-2019 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* Distributed under the Boost Software License, Version 1.0.
7
* See accompanying file license-boost.txt or copy at
8
9
#include <StGLCore/StGLCore20.h>
10
#include <StGL/StGLContext.h>
11
12
-/// TODO (Kirill Gavrilov#9) move to the common header
13
namespace {
14
static const GLfloat ST_PI = 3.1415926535897932384626433832795f;
15
static const GLfloat ST_TWOPI = 6.2831853071795864769252867665590f;
16
static const GLfloat ST_PIDIV2 = 1.5707963267948966192313216916397f;
17
-};
18
+}
19
20
StGLUVSphere::StGLUVSphere(const StGLVec3& theCenter,
21
const GLfloat theRadius,
22
- const size_t theRings)
23
+ const size_t theRings,
24
+ const bool theIsHemisphere)
25
: StGLMesh(GL_TRIANGLE_STRIP),
26
myPrimCounts(1),
27
myIndPointers(1),
28
myCenter(theCenter),
29
myRadius(theRadius),
30
- myRings(theRings) {
31
+ myRings(theRings),
32
+ myIsHemisphere(theIsHemisphere) {
33
//
34
}
35
36
37
myIndPointers(1),
38
myCenter(theBndSphere.getCenter()),
39
myRadius(theBndSphere.getRadius()),
40
- myRings(theRings) {
41
+ myRings(theRings),
42
+ myIsHemisphere(false) {
43
//
44
}
45
46
47
tcrd.y() = GLfloat(ringId) / GLfloat(aRingsCount);
48
49
for(size_t pointId = 0; pointId <= pointPerRing; ++pointId) {
50
- phi = GLfloat(pointId) * ST_TWOPI / GLfloat(pointPerRing);
51
+ if(myIsHemisphere) {
52
+ phi = ST_PIDIV2 + GLfloat(pointId) * ST_PI / GLfloat(pointPerRing);
53
+ } else {
54
+ phi = GLfloat(pointId) * ST_TWOPI / GLfloat(pointPerRing);
55
+ }
56
57
tcrd.x() = GLfloat(pointId) / GLfloat(pointPerRing);
58
59
sview-17_04.tar.gz/StShared/StImage.cpp -> sview-20_08.tar.gz/StShared/StImage.cpp
Changed
172
1
2
/**
3
- * Copyright © 2010-2015 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2010-2019 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* Distributed under the Boost Software License, Version 1.0.
7
* See accompanying file license-boost.txt or copy at
8
9
case ImgColor_RGB: return "ImgColor_RGB";
10
case ImgColor_RGBA: return "ImgColor_RGBA";
11
case ImgColor_GRAY: return "ImgColor_GRAY";
12
+ case ImgColor_XYZ: return "ImgColor_XYZ";
13
case ImgColor_YUV: return "ImgColor_YUV";
14
+ case ImgColor_YUVA: return "ImgColor_YUVA";
15
case ImgColor_CMYK: return "ImgColor_CMYK";
16
case ImgColor_HSV: return "ImgColor_HSV";
17
case ImgColor_HSL: return "ImgColor_HSL";
18
- default: return "ImgColor_UNKNOWN";
19
}
20
+ return "ImgColor_UNKNOWN";
21
#else
22
switch(theColorModel) {
23
case ImgColor_RGB: return "RGB";
24
case ImgColor_RGBA: return "RGBA";
25
case ImgColor_GRAY: return "Grayscale";
26
+ case ImgColor_XYZ: return "XYZ";
27
case ImgColor_YUV: return "YUV";
28
+ case ImgColor_YUVA: return "YUVA";
29
case ImgColor_CMYK: return "CMYK";
30
case ImgColor_HSV: return "HSV";
31
case ImgColor_HSL: return "HSL";
32
- default: return StString("UNKNOWN[") + theColorModel + "]";
33
}
34
+ return StString("UNKNOWN[") + theColorModel + "]";
35
#endif
36
}
37
38
+const char* StImage::formatImgPixelFormat() const {
39
+ switch(myColorModel) {
40
+ case ImgColor_RGB:
41
+ case ImgColor_RGBA:
42
+ case ImgColor_GRAY: {
43
+ switch(myPlanes[0].getFormat()) {
44
+ case StImagePlane::ImgGray: return "gray8";
45
+ case StImagePlane::ImgGray16: return "gray16";
46
+ case StImagePlane::ImgRGB: return "rgb24";
47
+ case StImagePlane::ImgBGR: return "bgr24";
48
+ case StImagePlane::ImgRGB32: return "rgb32";
49
+ case StImagePlane::ImgBGR32: return "bgr32";
50
+ case StImagePlane::ImgRGB48: return "rgb48";
51
+ case StImagePlane::ImgRGBA: return "rgba32";
52
+ case StImagePlane::ImgBGRA: return "bgra32";
53
+ case StImagePlane::ImgRGBA64: return "rgba64";
54
+ case StImagePlane::ImgGrayF: return "grayf";
55
+ case StImagePlane::ImgRGBF: return "rgbf";
56
+ case StImagePlane::ImgBGRF: return "bgrf";
57
+ case StImagePlane::ImgRGBAF: return "rgbaf";
58
+ case StImagePlane::ImgBGRAF: return "bgraf";
59
+ case StImagePlane::ImgUV: return "uv";
60
+ case StImagePlane::ImgUNKNOWN: return "unknown";
61
+ }
62
+ return "invalid_rgb";
63
+ }
64
+ case ImgColor_XYZ: {
65
+ switch(myPlanes[0].getFormat()) {
66
+ case StImagePlane::ImgRGB: return "xyz8";
67
+ case StImagePlane::ImgRGB48: return "xyz12";
68
+ case StImagePlane::ImgRGBF: return "xyzf";
69
+ default: break;
70
+ }
71
+ return "invalid_xyz";
72
+ }
73
+ case ImgColor_YUV:
74
+ case ImgColor_YUVA: {
75
+ const bool hasAlpha = myColorModel == ImgColor_YUVA;
76
+ const size_t aDelimX = (myPlanes[1].getSizeX() > 0) ? (myPlanes[0].getSizeX() / myPlanes[1].getSizeX()) : 1;
77
+ const size_t aDelimY = (myPlanes[1].getSizeY() > 0) ? (myPlanes[0].getSizeY() / myPlanes[1].getSizeY()) : 1;
78
+ if(myPlanes[1].getFormat() == StImagePlane::ImgUV) {
79
+ return "nv12";
80
+ } else if(aDelimX == 1 && aDelimY == 1) {
81
+ switch(myColorScale) {
82
+ case StImage::ImgScale_Mpeg:
83
+ return myPlanes[0].getFormat() == StImagePlane::ImgGray16
84
+ ? (hasAlpha ? "yuva444p16" : "yuv444p16")
85
+ : (hasAlpha ? "yuva444p" : "yuv444p");
86
+ case StImage::ImgScale_Mpeg9:
87
+ case StImage::ImgScale_Jpeg9:
88
+ return (hasAlpha ? "yuva444p9" : "yuv444p9");
89
+ case StImage::ImgScale_Mpeg10:
90
+ case StImage::ImgScale_Jpeg10:
91
+ return (hasAlpha ? "yuva444p10" : "yuv444p10");
92
+ case StImage::ImgScale_Full:
93
+ default:
94
+ return myPlanes[0].getFormat() == StImagePlane::ImgGray16
95
+ ? (hasAlpha ? "yuvaj444p16" : "yuvj444p16")
96
+ : (hasAlpha ? "yuvaj444p" : "yuvj444p");
97
+ }
98
+ } else if(aDelimX == 2 && aDelimY == 2) {
99
+ switch(myColorScale) {
100
+ case StImage::ImgScale_Mpeg:
101
+ return myPlanes[0].getFormat() == StImagePlane::ImgGray16
102
+ ? (hasAlpha ? "yuva420p16" : "yuv420p16")
103
+ : (hasAlpha ? "yuva420p" : "yuv420p");
104
+ case StImage::ImgScale_Mpeg9:
105
+ case StImage::ImgScale_Jpeg9:
106
+ return (hasAlpha ? "yuva420p9" : "yuv420p9");
107
+ case StImage::ImgScale_Mpeg10:
108
+ case StImage::ImgScale_Jpeg10:
109
+ return (hasAlpha ? "yuva420p10" : "yuv420p10");
110
+ case StImage::ImgScale_Full:
111
+ default:
112
+ return myPlanes[0].getFormat() == StImagePlane::ImgGray16
113
+ ? (hasAlpha ? "yuvaj420p16" : "yuvj420p16")
114
+ : (hasAlpha ? "yuvaj420p" : "yuvj420p");
115
+ }
116
+ } else if(aDelimX == 2 && aDelimY == 1) {
117
+ switch(myColorScale) {
118
+ case StImage::ImgScale_Mpeg:
119
+ return myPlanes[0].getFormat() == StImagePlane::ImgGray16
120
+ ? (hasAlpha ? "yuva422p16" : "yuv422p16")
121
+ : (hasAlpha ? "yuva422p" : "yuv422p");
122
+ case StImage::ImgScale_Mpeg9:
123
+ case StImage::ImgScale_Jpeg9:
124
+ return (hasAlpha ? "yuva422p9" : "yuv422p9");
125
+ case StImage::ImgScale_Mpeg10:
126
+ case StImage::ImgScale_Jpeg10:
127
+ return (hasAlpha ? "yuva422p10" : "yuv422p10");
128
+ case StImage::ImgScale_Full:
129
+ default:
130
+ return myPlanes[0].getFormat() == StImagePlane::ImgGray16
131
+ ? (hasAlpha ? "yuvaj422p16" : "yuvj422p16")
132
+ : (hasAlpha ? "yuvaj422p" : "yuvj422p");
133
+ }
134
+ } else if(aDelimX == 1 && aDelimY == 2) {
135
+ return myColorScale == StImage::ImgScale_Mpeg
136
+ ? (hasAlpha ? "yuva440p" : "yuv440p")
137
+ : (hasAlpha ? "yuvaj440p" : "yuvj440p");
138
+ } else if(aDelimX == 4 && aDelimY == 1) {
139
+ return myColorScale == StImage::ImgScale_Mpeg
140
+ ? (hasAlpha ? "yuva411p" : "yuv411p")
141
+ : (hasAlpha ? "yuvaj411p" : "yuvj411p");
142
+ } else if(aDelimX == 4 && aDelimY == 4) {
143
+ return myColorScale == StImage::ImgScale_Mpeg
144
+ ? (hasAlpha ? "yuva410p" : "yuv410p")
145
+ : (hasAlpha ? "yuvaj410p" : "yuvj410p");
146
+ }
147
+ return (hasAlpha ? "yuva_unknown" : "yuv_unknown");
148
+ }
149
+ case ImgColor_CMYK:
150
+ return "CMYK";
151
+ case ImgColor_HSV:
152
+ return "HSV";
153
+ case ImgColor_HSL:
154
+ return "HSL";
155
+ }
156
+ return "unknown";
157
+}
158
+
159
StImage::StImage()
160
: myPAR(1.0f),
161
myColorModel(ImgColor_RGB),
162
163
const StImage& theImageR,
164
const int theSeparationDx,
165
const int theSeparationDy) {
166
- const bool isYUV = theImageL.getColorModel() == StImage::ImgColor_YUV;
167
+ const bool isYUV = theImageL.getColorModel() == StImage::ImgColor_YUV
168
+ || theImageL.getColorModel() == StImage::ImgColor_YUVA;
169
for(size_t aPlaneId = 0; aPlaneId < 4; ++aPlaneId) {
170
float aScaleX = (theImageL.getPlane(aPlaneId).getSizeX() > 0) ? theImageL.getScaleFactorX(aPlaneId) : 1.0f;
171
float aScaleY = (theImageL.getPlane(aPlaneId).getSizeY() > 0) ? theImageL.getScaleFactorY(aPlaneId) : 1.0f;
172
sview-17_04.tar.gz/StShared/StImageFile.cpp -> sview-20_08.tar.gz/StShared/StImageFile.cpp
Changed
223
1
2
/**
3
- * Copyright © 2010-2015 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2010-2020 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* Distributed under the Boost Software License, Version 1.0.
7
* See accompanying file license-boost.txt or copy at
8
9
#include <StImage/StDevILImage.h>
10
#include <StImage/StFreeImage.h>
11
#include <StImage/StWebPImage.h>
12
+#include <StImage/StStbImage.h>
13
#include <StAV/StAVImage.h>
14
#include <StFile/StFileNode.h>
15
#include <StFile/StMIME.h>
16
+#include <StFile/StRawFile.h>
17
18
#include <StStrings/StLogger.h>
19
20
+/**
21
+ * DDS Pixel Format structure.
22
+ */
23
+struct StDDSPixelFormat {
24
+ uint32_t Size;
25
+ uint32_t Flags;
26
+ uint32_t FourCC;
27
+ uint32_t RGBBitCount;
28
+ uint32_t RBitMask;
29
+ uint32_t GBitMask;
30
+ uint32_t BBitMask;
31
+ uint32_t ABitMask;
32
+};
33
+
34
+/**
35
+ * DDS File header structure.
36
+ */
37
+struct StDDSFileHeader {
38
+ /**
39
+ * Caps2 flag indicating complete (6 faces) cubemap.
40
+ */
41
+ enum { DDSCompleteCubemap = 0xFE00 };
42
+
43
+ /**
44
+ * Return TRUE if cubmap flag is set.
45
+ */
46
+ bool isCompleteCubemap() const { return (Caps2 & DDSCompleteCubemap) != 0; }
47
+
48
+ uint32_t Size;
49
+ uint32_t Flags;
50
+ uint32_t Height;
51
+ uint32_t Width;
52
+ uint32_t PitchOrLinearSize;
53
+ uint32_t Depth;
54
+ uint32_t MipMapCount;
55
+ uint32_t Reserved1[11];
56
+ StDDSPixelFormat PixelFormatDef;
57
+ uint32_t Caps;
58
+ uint32_t Caps2;
59
+ uint32_t Caps3;
60
+ uint32_t Caps4;
61
+ uint32_t Reserved2;
62
+};
63
+
64
StImageFile::StImageFile()
65
-: mySrcFormat(StFormat_AUTO) {
66
+: mySrcFormat(StFormat_AUTO),
67
+ mySrcPanorama(StPanorama_OFF) {
68
//
69
}
70
71
72
} else if(thePreferred.isEqualsIgnoreCase(stCString("WebP")) ||
73
thePreferred.isEqualsIgnoreCase(stCString("StWebPImage"))) {
74
aPreferred = ST_WEBP;
75
+ } else if(thePreferred.isEqualsIgnoreCase(stCString("stb"))) {
76
+ aPreferred = ST_STB;
77
}
78
return aPreferred;
79
}
80
81
case ST_FREEIMAGE: return "FreeImage";
82
case ST_DEVIL: return "DevIL";
83
case ST_WEBP: return "WebP";
84
+ case ST_STB: return "stb";
85
default:
86
case ST_LIBAV: return "FFmpeg";
87
}
88
89
} else if(anExt.isEqualsIgnoreCase(stCString("webpll"))
90
|| theMIMEType.getMIMEType().isEquals(stCString("image/webpll"))) {
91
return StImageFile::ST_TYPE_WEBPLL;
92
+ } else if(anExt.isEqualsIgnoreCase(stCString("dds"))
93
+ || theMIMEType.getMIMEType().isEquals(stCString("image/vnd-ms.dds"))) {
94
+ return StImageFile::ST_TYPE_DDS;
95
}
96
return StImageFile::ST_TYPE_NONE;
97
}
98
99
}
100
break;
101
}
102
+ case ST_STB: {
103
+ if(StStbImage::init()) {
104
+ return new StStbImage();
105
+ }
106
+ break;
107
+ }
108
default:
109
case ST_LIBAV: {
110
if(StAVImage::init()) {
111
112
return StHandle<StImageFile>();
113
}
114
115
+bool StImageFile::load(const StString& theFilePath,
116
+ ImageType theImageType,
117
+ uint8_t* theDataPtr, int theDataSize) {
118
+ if(theImageType == ST_TYPE_DDS) {
119
+ // Most image libraries ignore arrays/cubemaps in DDS file.
120
+ // As DDS format is pretty simple - parse it here and load cubemap as vertically stacked image.
121
+ StRawFile aRawFile(theFilePath);
122
+ if(theDataPtr == NULL) {
123
+ if(!aRawFile.readFile()) {
124
+ return loadExtra(theFilePath, theImageType, theDataPtr, theDataSize, false);
125
+ }
126
+ theDataPtr = (uint8_t* )aRawFile.getBuffer();
127
+ theDataSize = (int )aRawFile.getSize();
128
+ }
129
+
130
+ if (theDataSize < 128
131
+ || memcmp (&theDataPtr[0], "DDS ", 4) != 0) {
132
+ return loadExtra(theFilePath, theImageType, theDataPtr, theDataSize, false);
133
+ }
134
+
135
+ const StDDSFileHeader* aSrcHeader = (const StDDSFileHeader* )&theDataPtr[4];
136
+ if (aSrcHeader->Size != 124
137
+ || aSrcHeader->Width == 0
138
+ || aSrcHeader->Height == 0
139
+ || aSrcHeader->Width != aSrcHeader->Height
140
+ || aSrcHeader->PixelFormatDef.Size != 32
141
+ || (aSrcHeader->Caps2 & StDDSFileHeader::DDSCompleteCubemap) != StDDSFileHeader::DDSCompleteCubemap) {
142
+ return loadExtra(theFilePath, theImageType, theDataPtr, theDataSize, false);
143
+ }
144
+
145
+ const int aHeaderSize = aSrcHeader->Size + 4;
146
+ const int aPayLoadSize = theDataSize - aHeaderSize;
147
+ if (aPayLoadSize % 6 != 0
148
+ || aPayLoadSize <= 0) {
149
+ return loadExtra(theFilePath, theImageType, theDataPtr, theDataSize, false);
150
+ }
151
+
152
+ const int aTileDataSize = aPayLoadSize / 6;
153
+ StArray<uint8_t> aTileBuffer (aTileDataSize + aHeaderSize);
154
+ memcpy(&aTileBuffer.changeFirst(), "DDS ", 4);
155
+ memcpy(&aTileBuffer.changeValue(4), aSrcHeader, aSrcHeader->Size);
156
+ StDDSFileHeader* aHeaderTile = (StDDSFileHeader* )&aTileBuffer.changeValue(4);
157
+ aHeaderTile->Caps2 &= ~(StDDSFileHeader::DDSCompleteCubemap);
158
+
159
+ StHandle<StImageFile> aTileImage = createEmpty();
160
+
161
+ memcpy(&aTileBuffer.changeValue(aHeaderSize), &theDataPtr[aHeaderSize], aTileDataSize);
162
+ if(!aTileImage->loadExtra(theFilePath, theImageType, &aTileBuffer.changeFirst(), (int )aTileBuffer.size(), false)
163
+ || aTileImage->isNull()
164
+ || aTileImage->getSizeX() < 1
165
+ || aTileImage->getSizeY() < 1
166
+ || aTileImage->getSizeX() != aTileImage->getSizeY()) {
167
+ return loadExtra(theFilePath, theImageType, theDataPtr, theDataSize, false);
168
+ }
169
+
170
+ close();
171
+ nullify();
172
+ myMetadata = aTileImage->myMetadata;
173
+ myStateDescr = aTileImage->myStateDescr;
174
+ mySrcFormat = aTileImage->mySrcFormat;
175
+ setColorModel(aTileImage->getColorModel());
176
+ setColorScale(aTileImage->getColorScale());
177
+ setPixelRatio(aTileImage->getPixelRatio());
178
+ const bool isTopDownLayout = aTileImage->isTopDown();
179
+ for(size_t aPlaneId = 0; aPlaneId < 4; ++aPlaneId) {
180
+ const StImagePlane& aFromPlane = aTileImage->getPlane(aPlaneId);
181
+ const size_t aTileIndex = isTopDownLayout ? 0 : 5;
182
+ if(!aFromPlane.isNull()) {
183
+ if(!changePlane(aPlaneId).initTrash(aFromPlane.getFormat(), aFromPlane.getSizeX(), aFromPlane.getSizeX() * 6)) {
184
+ return false;
185
+ }
186
+ changePlane(aPlaneId).setTopDown(aFromPlane.isTopDown());
187
+ memcpy(changePlane(aPlaneId).changeData() + aFromPlane.getSizeBytes() * aTileIndex,
188
+ aFromPlane.getData(), aFromPlane.getSizeBytes());
189
+ }
190
+ }
191
+
192
+ for(size_t aTileIter = 1; aTileIter < 6; ++aTileIter) {
193
+ memcpy(&aTileBuffer.changeValue(aHeaderSize), &theDataPtr[aTileIter * aTileDataSize + aHeaderSize], aTileDataSize);
194
+ aTileImage = createEmpty();
195
+ if(!aTileImage->loadExtra(theFilePath, theImageType, &aTileBuffer.changeFirst(), (int )aTileBuffer.size(), false)
196
+ || aTileImage->isNull()
197
+ || aTileImage->getSizeX() != getSizeX()
198
+ || aTileImage->getSizeY() != getSizeX() // square
199
+ || aTileImage->getColorModel() != getColorModel()
200
+ || aTileImage->getPlane().getFormat() != getPlane().getFormat()) {
201
+ ST_ERROR_LOG("Internal error: DDS file is decoded into inconsistent tiles");
202
+ return loadExtra(theFilePath, theImageType, theDataPtr, theDataSize, false);
203
+ }
204
+
205
+ const size_t aTileIndex = isTopDownLayout ? aTileIter : (5 - aTileIter);
206
+ for(size_t aPlaneId = 0; aPlaneId < 4; ++aPlaneId) {
207
+ const StImagePlane& aFromPlane = aTileImage->getPlane(aPlaneId);
208
+ if(!aFromPlane.isNull()) {
209
+ memcpy(changePlane(aPlaneId).changeData() + aFromPlane.getSizeBytes() * aTileIndex,
210
+ aFromPlane.getData(), aFromPlane.getSizeBytes());
211
+ }
212
+ }
213
+ }
214
+ mySrcPanorama = StPanorama_Cubemap1_6;
215
+ return true;
216
+ }
217
+ return loadExtra(theFilePath, theImageType, theDataPtr, theDataSize, false);
218
+}
219
+
220
StImageFileCounter::~StImageFileCounter() {}
221
222
void StImageFileCounter::createReference(StHandle<StBufferCounter>& theOther) const {
223
sview-17_04.tar.gz/StShared/StImagePlane.cpp -> sview-20_08.tar.gz/StShared/StImagePlane.cpp
Changed
50
1
2
/**
3
- * Copyright © 2010-2015 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2010-2020 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* Distributed under the Boost Software License, Version 1.0.
7
* See accompanying file license-boost.txt or copy at
8
9
case ImgRGBAF: return "ImgRGBAF";
10
case ImgBGRAF: return "ImgBGRAF";
11
case ImgUV: return "ImgUV";
12
- case ImgUNKNOWN:
13
- default: return "ImgUNKNOWN";
14
+ case ImgUNKNOWN: return "ImgUNKNOWN";
15
}
16
+ return "unknown";
17
}
18
19
StImagePlane::StImagePlane()
20
21
return true;
22
}
23
24
+bool StImagePlane::initTransposedCopy(const StImagePlane& theCopy,
25
+ const bool theIsClockwise) {
26
+ if(myImgFormat != theCopy.myImgFormat
27
+ || mySizeX != theCopy.mySizeX
28
+ || mySizeY != theCopy.mySizeY) {
29
+ if(!initTrash(theCopy.myImgFormat, theCopy.mySizeY, theCopy.mySizeX)) {
30
+ return false;
31
+ }
32
+ }
33
+
34
+ const size_t aPixelSize = getSizePixelBytes();
35
+ const size_t aSrcColFrom = theIsClockwise ? theCopy.mySizeX - 1 : 0;
36
+ const size_t aSrcRowFrom = !theIsClockwise ? theCopy.mySizeY - 1 : 0;
37
+ const size_t aSrcColIncr = aSrcColFrom == 0 ? 1 : size_t(-1);
38
+ const size_t aSrcRowIncr = aSrcRowFrom == 0 ? 1 : size_t(-1);
39
+ for(size_t aDstRow = 0, aSrcCol = aSrcColFrom; aDstRow < mySizeY; ++aDstRow, aSrcCol += aSrcColIncr) {
40
+ for(size_t aDstCol = 0, aSrcRow = aSrcRowFrom; aDstCol < mySizeX; ++aDstCol, aSrcRow += aSrcRowIncr) {
41
+ stMemCpy(changeData(aDstRow, aDstCol), theCopy.getData(aSrcRow, aSrcCol), aPixelSize);
42
+ }
43
+ }
44
+ return true;
45
+}
46
+
47
bool StImagePlane::initWrapper(const StImagePlane& theCopy) {
48
if(!initWrapper(theCopy.myImgFormat, theCopy.myDataPtr,
49
theCopy.mySizeX, theCopy.mySizeY, theCopy.mySizeRowBytes)) {
50
sview-20_08.tar.gz/StShared/StJNIEnv.cpp
Added
77
1
2
+/**
3
+ * Copyright © 2019 Kirill Gavrilov <kirill@sview.ru>
4
+ *
5
+ * Distributed under the Boost Software License, Version 1.0.
6
+ * See accompanying file license-boost.txt or copy at
7
+ * http://www.boost.org/LICENSE_1_0.txt
8
+ */
9
+
10
+#include <StJNI/StJNIEnv.h>
11
+
12
+#include <StStrings/StLogger.h>
13
+#include <StThreads/StThread.h>
14
+
15
+#if defined(__ANDROID__)
16
+ #include <jni.h>
17
+#endif
18
+
19
+StJNIEnv::StJNIEnv(JavaVM* theJavaVM)
20
+: myJavaVM(theJavaVM),
21
+ myJniEnv(NULL),
22
+ myThreadId(0),
23
+ myToDetach(false) {
24
+ if(myJavaVM == NULL) {
25
+ return;
26
+ }
27
+
28
+#if defined(__ANDROID__)
29
+ void* aJniEnv = NULL;
30
+ switch(myJavaVM->GetEnv(&aJniEnv, JNI_VERSION_1_6)) {
31
+ case JNI_EDETACHED: {
32
+ if(myJavaVM->AttachCurrentThread(&myJniEnv, NULL) < 0) {
33
+ myJniEnv = NULL;
34
+ ST_ERROR_LOG("Failed to attach working thread to Java VM");
35
+ return;
36
+ }
37
+ myToDetach = true;
38
+ myThreadId = StThread::getCurrentThreadId();
39
+ break;
40
+ }
41
+ case JNI_OK: {
42
+ myJniEnv = (JNIEnv* )aJniEnv;
43
+ myToDetach = false;
44
+ break;
45
+ }
46
+ case JNI_EVERSION: {
47
+ ST_ERROR_LOG("Failed to attach working thread to Java VM - JNI version is not supported");
48
+ break;
49
+ }
50
+ default: {
51
+ ST_ERROR_LOG("Failed to attach working thread to Java VM");
52
+ break;
53
+ }
54
+ }
55
+#endif
56
+}
57
+
58
+StJNIEnv::~StJNIEnv() {
59
+ detach();
60
+}
61
+
62
+void StJNIEnv::detach() {
63
+ if(myJavaVM != NULL
64
+ && myJniEnv != NULL
65
+ && myToDetach) {
66
+ if(myThreadId != StThread::getCurrentThreadId()) {
67
+ ST_ERROR_LOG("Internal error, StJNIEnv::detach() - attempt to detach from another thread");
68
+ }
69
+ #if defined(__ANDROID__)
70
+ myJavaVM->DetachCurrentThread();
71
+ #endif
72
+ }
73
+
74
+ myJniEnv = NULL;
75
+ myToDetach = false;
76
+}
77
sview-17_04.tar.gz/StShared/StJpegParser.cpp -> sview-20_08.tar.gz/StShared/StJpegParser.cpp
Changed
119
1
2
StJpegParser::StJpegParser(const StCString& theFilePath)
3
: StRawFile(theFilePath),
4
myImages(NULL),
5
- myStFormat(StFormat_AUTO) {
6
+ myStFormat(StFormat_AUTO),
7
+ myPanorama(StPanorama_OFF) {
8
stMemZero(myOffsets, sizeof(myOffsets));
9
#if !defined(_MSC_VER)
10
(void )markerString;
11
12
// destroy all images
13
myImages.nullify();
14
myComment.clear();
15
+ myXMP.clear();
16
myStFormat = StFormat_AUTO;
17
+ myPanorama = StPanorama_OFF;
18
myLength = 0;
19
stMemZero(myOffsets, sizeof(myOffsets));
20
}
21
22
// parse the data
23
StHandle<StJpegParser::Image> anImg = new StJpegParser::Image();
24
anImg->Data = aData - 2;
25
+ bool toDetectCubemap = false;
26
27
for(;;) {
28
// search for the next marker in the file
29
30
//ST_DEBUG_LOG(" #" + theImgCount + "." + theDepth + " [" + markerString(aMarker) + "] at position " + size_t(aData - myBuffer) + " / " + myLength); ///
31
if(aMarker == M_EOI) {
32
//ST_DEBUG_LOG("Jpeg, EOI at position " + size_t(aData - myBuffer) + " / " + myLength);
33
+
34
+ bool isPanoStereo = false;
35
+ if(toDetectCubemap && myPanorama == StPanorama_OFF) {
36
+ size_t aViewX = anImg->SizeX, aViewY = anImg->SizeY;
37
+ if(myStFormat == StFormat_SideBySide_LR || myStFormat == StFormat_SideBySide_RL) {
38
+ aViewX /= 2;
39
+ } else if(myStFormat == StFormat_TopBottom_LR || myStFormat == StFormat_TopBottom_RL) {
40
+ aViewY /= 2;
41
+ }
42
+ if(aViewX == aViewY * 6) {
43
+ myPanorama = StPanorama_Cubemap6_1;
44
+ } else if(aViewX * 6 == aViewY) {
45
+ myPanorama = StPanorama_Cubemap1_6;
46
+ } else if(aViewX * 2 == aViewY * 3) {
47
+ myPanorama = StPanorama_Cubemap3_2;
48
+ }
49
+ } else if(anImg->get360PanoMakerNote(isPanoStereo)) {
50
+ if(myPanorama == StPanorama_OFF) {
51
+ myPanorama = StPanorama_Sphere;
52
+ }
53
+ if(myStFormat == StFormat_AUTO
54
+ && isPanoStereo) {
55
+ myStFormat = StFormat_TopBottom_LR;
56
+ }
57
+ }
58
+
59
anImg->Length = size_t(aData - anImg->Data);
60
return anImg;
61
} else if(aMarker == M_SOI) {
62
63
}
64
} else if(stAreEqual(aData + 2, "http:", 5)) {
65
//ST_DEBUG_LOG("Image cotains XMP section");
66
+ if(stAreEqual(aData + 2, "http://ns.adobe.com/xap/1.0/", 28)) { // XMP basic namespace
67
+ myXMP = StString((char* )aData + 31, anItemLen - 31);
68
+ {
69
+ // GPano http://ns.google.com/photos/1.0/panorama/ namespace metadata.
70
+ // Note possible cropped panorama parameters are ignored by sView.
71
+ if(myXMP.isContains(stCString("<GPano:ProjectionType>equirectangular</GPano:ProjectionType>"))
72
+ || myXMP.isContains(stCString("GPano:ProjectionType=\"equirectangular\""))) {
73
+ // Google currently supports only equirectangular format
74
+ myPanorama = StPanorama_Sphere;
75
+ } else if(myXMP.isContains(stCString("<GPano:ProjectionType>cubemap</GPano:ProjectionType>"))
76
+ || myXMP.isContains(stCString("GPano:ProjectionType=\"cubemap\""))) {
77
+ // this one doesn't yet exist, but try to support it
78
+ toDetectCubemap = true;
79
+ }
80
+ }
81
+ myXMP.clear();
82
+ }
83
} else {
84
//ST_DEBUG_LOG(" @@@ APP2 " + StString((char* )aData + 2));
85
}
86
87
return false;
88
}
89
stMemCpy(aNewData, myBuffer, myLength);
90
- stMemFreeAligned(myBuffer);
91
+ if(myIsOwnData) {
92
+ stMemFreeAligned(myBuffer);
93
+ }
94
+ myIsOwnData = true;
95
96
// update pointers of image(s) data
97
for(StHandle<StJpegParser::Image> anImg = myImages;
98
99
return aString;
100
}
101
102
+bool StJpegParser::Image::get360PanoMakerNote(bool& theIsStereo) const {
103
+ StExifDir::Query aQuery(StExifDir::DType_General, StExifTags::Image_MakerNote, StExifEntry::FMT_STRING);
104
+ if(!StExifDir::findEntry(Exif, aQuery)) {
105
+ return false;
106
+ } else if(::strncmp((char* )aQuery.Entry.ValuePtr, "360Stereo", 9) == 0) {
107
+ theIsStereo = true;
108
+ return true;
109
+ } else if(::strncmp((char* )aQuery.Entry.ValuePtr, "360Mono", 7) == 0) {
110
+ theIsStereo = false;
111
+ return true;
112
+ }
113
+ return false;
114
+}
115
+
116
bool StJpegParser::Image::getParallax(double& theParallax) const {
117
StExifDir::Query aQuery(StExifDir::DType_MakerFuji, StExifTags::Fuji_Parallax);
118
if(!StExifDir::findEntry(Exif, aQuery)
119
sview-17_04.tar.gz/StShared/StLogger.ObjC.mm -> sview-20_08.tar.gz/StShared/StLogger.ObjC.mm
Changed
42
1
2
StLogger::GetDefault().write(theMessage, StLogger::ST_INFO);
3
StCocoaLocalPool aLocalPool;
4
NSString* aMessage = [NSString stringWithUTF8String: theMessage.toCString()];
5
+ST_DISABLE_DEPRECATION_WARNINGS
6
NSRunAlertPanel(@"Info", @"%@", @"OK", nil, nil, aMessage);
7
+ST_ENABLE_DEPRECATION_WARNINGS
8
}
9
10
void StMessageBox::Warn(const StString& theMessage) {
11
12
StLogger::GetDefault().write(theMessage, StLogger::ST_WARNING);
13
StCocoaLocalPool aLocalPool;
14
NSString* aMessage = [NSString stringWithUTF8String: theMessage.toCString()];
15
+ST_DISABLE_DEPRECATION_WARNINGS
16
NSRunAlertPanel(@"Warning", @"%@", @"OK", nil, nil, aMessage);
17
+ST_ENABLE_DEPRECATION_WARNINGS
18
}
19
20
void StMessageBox::Error(const StString& theMessage) {
21
22
StLogger::GetDefault().write(theMessage, StLogger::ST_ERROR);
23
StCocoaLocalPool aLocalPool;
24
NSString* aMessage = [NSString stringWithUTF8String: theMessage.toCString()];
25
+ST_DISABLE_DEPRECATION_WARNINGS
26
NSRunAlertPanel(@"Error", @"%@", @"OK", nil, nil, aMessage);
27
+ST_ENABLE_DEPRECATION_WARNINGS
28
}
29
30
bool StMessageBox::Question(const StString& theMessage) {
31
32
}
33
StCocoaLocalPool aLocalPool;
34
NSString* aMessage = [NSString stringWithUTF8String: theMessage.toCString()];
35
+ST_DISABLE_DEPRECATION_WARNINGS
36
int aResult = NSRunAlertPanel(@"Question", @"%@", @"Yes", @"No", nil, aMessage);
37
return aResult == NSAlertDefaultReturn;
38
+ST_ENABLE_DEPRECATION_WARNINGS
39
}
40
41
#endif // __APPLE__
42
sview-17_04.tar.gz/StShared/StPlayList.cpp -> sview-20_08.tar.gz/StShared/StPlayList.cpp
Changed
25
1
2
}
3
4
if(myCurrent != NULL) {
5
- if(aRemItem->getPlayedFlag() != aPlayedFlag) {
6
+ if(myCurrent->getPlayedFlag() != aPlayedFlag) {
7
// the item has not been played yet - mark it as such
8
- aRemItem->setPlayedFlag(aPlayedFlag);
9
+ myCurrent->setPlayedFlag(aPlayedFlag);
10
} else {
11
// one played item has been removed
12
--myPlayedCount;
13
14
}
15
} else {
16
// not a filesystem element - probably url or invalid path
17
- StFileNode* aFileNode = new StFileNode(thePath, &myFoldersRoot);
18
+ StFolder* aSubFolder = new StFolder(stCString(""), &myFoldersRoot);
19
+ myFoldersRoot.add(aSubFolder);
20
+
21
+ StFileNode* aFileNode = new StFileNode(thePath, aSubFolder);
22
myFoldersRoot.add(aFileNode);
23
addRecentFile(*aFileNode); // append to recent files list
24
addPlayItem(new StPlayItem(aFileNode, myDefStParams));
25
sview-17_04.tar.gz/StShared/StProcess.cpp -> sview-20_08.tar.gz/StShared/StProcess.cpp
Changed
13
1
2
static const StString STCORE_NAME = StString("StCore") + ST_DLIB_SUFFIX;
3
#else
4
static const StString STCORE_NAME = StString("libStCore") + ST_DLIB_SUFFIX;
5
+#ifndef APP_PREFIX
6
static const StString ST_DEFAULT_PATH = "/usr/share/sView/";
7
+#else
8
+ static const StString ST_DEFAULT_PATH = APP_PREFIX"/share/sView/";
9
+#endif
10
#endif
11
12
inline bool isValidStSharePath(const StString& thePath) {
13
sview-17_04.tar.gz/StShared/StRawFile.cpp -> sview-20_08.tar.gz/StShared/StRawFile.cpp
Changed
38
1
2
myFileHandle(NULL),
3
myBuffer(NULL),
4
myBuffSize(0),
5
- myLength(0) {
6
+ myLength(0),
7
+ myIsOwnData(false) {
8
//
9
}
10
11
12
return;
13
}
14
freeBuffer();
15
+ myIsOwnData = true;
16
myBuffSize = theDataSize;
17
myBuffer = stMemAllocAligned<stUByte_t*>(myBuffSize + 1);
18
myBuffer[myBuffSize] = '\0'; // just for safe
19
}
20
21
+void StRawFile::wrapBuffer(stUByte_t* theBuffer,
22
+ size_t theDataSize) {
23
+ freeBuffer();
24
+ myIsOwnData = false;
25
+ myBuffSize = theDataSize;
26
+ myBuffer = theBuffer;
27
+}
28
+
29
void StRawFile::freeBuffer() {
30
- stMemFreeAligned(myBuffer);
31
+ if(myIsOwnData) {
32
+ stMemFreeAligned(myBuffer);
33
+ myIsOwnData = false;
34
+ }
35
myBuffer = NULL;
36
myBuffSize = 0;
37
}
38
sview-17_04.tar.gz/StShared/StResourceManager.cpp -> sview-20_08.tar.gz/StShared/StResourceManager.cpp
Changed
76
1
2
3
StResourceManager::StResourceManager(const StString& theAppName)
4
: myAppName(theAppName),
5
- myUserHomeFolder(StProcess::getEnv(StString("HOME")) + SYS_FS_SPLITTER),
6
+ myUserHomeFolder(StProcess::getEnv(StString("HOME"))),
7
myResFolder(StProcess::getStShareFolder()),
8
myLang("en") {
9
-
10
+#if !defined(__ANDROID__)
11
+ myFolders[FolderId_Documents] = myUserHomeFolder;
12
+#endif
13
+ myUserHomeFolder += SYS_FS_SPLITTER;
14
#if defined(_WIN32)
15
StString anAppDataLocal, anAppDataLocalLow, anAppDataRoam;
16
wchar_t* aPath = NULL;
17
18
}
19
if(::SHGetKnownFolderPath(FOLDERID_Documents, 0, NULL, &aPath) == S_OK) {
20
myUserHomeFolder.fromUnicode(aPath);
21
+ myFolders[FolderId_Documents] = myUserHomeFolder;
22
myUserHomeFolder += "\\";
23
::CoTaskMemFree(aPath);
24
}
25
26
StFolder::createFolder(myUserHomeFolder + "Library/Caches");
27
#else
28
// Linux world
29
- myUserDataFolder = myUserHomeFolder + ".local/share/" + myAppName + "/";
30
- mySettingsFolder = myUserHomeFolder + ".config/" + myAppName + "/";
31
- myCacheFolder = myUserHomeFolder + ".cache/" + myAppName + "/";
32
+ myUserDataFolder = StProcess::getEnv(StString("XDG_DATA_HOME"));
33
+ if(myUserDataFolder.isEmpty()) {
34
+ myUserDataFolder = myUserHomeFolder + ".local/share";
35
+ StFolder::createFolder(myUserHomeFolder + ".local");
36
+ StFolder::createFolder(myUserDataFolder);
37
+ }
38
+ myUserDataFolder = myUserDataFolder + "/" + myAppName + "/";
39
+
40
+ mySettingsFolder = StProcess::getEnv(StString("XDG_CONFIG_HOME"));
41
+ if(mySettingsFolder.isEmpty()) {
42
+ mySettingsFolder = myUserHomeFolder + ".config";
43
+ StFolder::createFolder(mySettingsFolder);
44
+ }
45
+ mySettingsFolder = mySettingsFolder + "/" + myAppName + "/";
46
+
47
+ myCacheFolder = StProcess::getEnv(StString("XDG_CACHE_HOME"));
48
+ if(myCacheFolder.isEmpty()) {
49
+ myCacheFolder = myUserHomeFolder + ".cache";
50
+ StFolder::createFolder(myCacheFolder);
51
+ }
52
+ myCacheFolder = myCacheFolder + "/" + myAppName + "/";
53
54
myFolders[FolderId_Downloads] = myUserHomeFolder + "Downloads";
55
myFolders[FolderId_Pictures] = myUserHomeFolder + "Pictures";
56
myFolders[FolderId_Music] = myUserHomeFolder + "Music";
57
myFolders[FolderId_Videos] = myUserHomeFolder + "Videos";
58
-
59
- // make sure parent paths are also exist (on broken home)
60
- StFolder::createFolder(myUserHomeFolder + ".local");
61
- StFolder::createFolder(myUserHomeFolder + ".local/share");
62
- StFolder::createFolder(myUserHomeFolder + ".config");
63
- StFolder::createFolder(myUserHomeFolder + ".cache");
64
#endif
65
66
StFolder::createFolder(myUserDataFolder);
67
68
myLang = aSysLoc.subString(0, 2);
69
} else if(aSysLoc.isStartsWith(stCString("russian"))) {
70
myLang = "ru";
71
+ } else if(aSysLoc.isStartsWith(stCString("spanish"))) {
72
+ myLang = "es";
73
} else if(aSysLoc.isStartsWith(stCString("french"))) {
74
myLang = "fr";
75
} else if(aSysLoc.isStartsWith(stCString("german"))) {
76
sview-17_04.tar.gz/StShared/StShared.cbp -> sview-20_08.tar.gz/StShared/StShared.cbp
Changed
33
1
2
<Unit filename="StGLTexture.cpp" />
3
<Unit filename="StGLTextureData.cpp" />
4
<Unit filename="StGLTextureQueue.cpp" />
5
+ <Unit filename="StGLUVCylinder.cpp" />
6
<Unit filename="StGLUVSphere.cpp" />
7
<Unit filename="StGLVertexBuffer.cpp" />
8
<Unit filename="StImage.cpp" />
9
10
</Unit>
11
<Unit filename="StResourceManager.cpp" />
12
<Unit filename="StSettings.cpp" />
13
+ <Unit filename="StStbImage.cpp" />
14
<Unit filename="StSocket.ObjC.mm">
15
<Option compile="1" />
16
<Option link="1" />
17
18
<Unit filename="../include/StGLMesh/StGLMesh.h" />
19
<Unit filename="../include/StGLMesh/StGLPrism.h" />
20
<Unit filename="../include/StGLMesh/StGLQuads.h" />
21
+ <Unit filename="../include/StGLMesh/StGLUVCylinder.h" />
22
<Unit filename="../include/StGLMesh/StGLUVSphere.h" />
23
<Unit filename="../include/StGLStereo/StFormatEnum.h" />
24
<Unit filename="../include/StGLStereo/StGLProjCamera.h" />
25
26
<Unit filename="../include/StImage/StImagePlane.h" />
27
<Unit filename="../include/StImage/StJpegParser.h" />
28
<Unit filename="../include/StImage/StPixelRGB.h" />
29
+ <Unit filename="../include/StImage/StStbImage.h" />
30
<Unit filename="../include/StImage/StWebPImage.h" />
31
<Unit filename="../include/StLibrary.h" />
32
<Unit filename="../include/StSettings/StEnumParam.h" />
33
sview-17_04.tar.gz/StShared/StShared.rc -> sview-20_08.tar.gz/StShared/StShared.rc
Changed
10
1
2
BEGIN
3
VALUE "FileDescription", "sView common algorithms library\000"
4
VALUE "FileVersion", SVIEW_SDK_VER_STRING "\000"
5
- VALUE "LegalCopyright", "\251 2007-2017 Kirill Gavrilov\000"
6
+ VALUE "LegalCopyright", "\251 2007-2020 Kirill Gavrilov and sView developers\000"
7
VALUE "ProductName", "StShared\000"
8
VALUE "ProductVersion", SVIEW_SDK_VER_STRING "\000"
9
VALUE "OfficialSite", "www.sview.ru\000"
10
sview-17_04.tar.gz/StShared/StShared.vcxproj -> sview-20_08.tar.gz/StShared/StShared.vcxproj
Changed
33
1
2
<ClCompile Include="StGLTexture.cpp" />
3
<ClCompile Include="StGLTextureData.cpp" />
4
<ClCompile Include="StGLTextureQueue.cpp" />
5
+ <ClCompile Include="StGLUVCylinder.cpp" />
6
<ClCompile Include="StGLUVSphere.cpp" />
7
<ClCompile Include="StGLVertexBuffer.cpp" />
8
<ClCompile Include="StImage.cpp" />
9
10
<ClCompile Include="StRegisterImpl.cpp" />
11
<ClCompile Include="StResourceManager.cpp" />
12
<ClCompile Include="StSettings.cpp" />
13
+ <ClCompile Include="StStbImage.cpp" />
14
<ClCompile Include="StDictionary.cpp" />
15
<ClCompile Include="StThread.cpp" />
16
<ClCompile Include="StTranslations.cpp" />
17
18
<ClInclude Include="..\include\StGLMesh\StGLMesh.h" />
19
<ClInclude Include="..\include\StGLMesh\StGLPrism.h" />
20
<ClInclude Include="..\include\StGLMesh\StGLQuads.h" />
21
+ <ClInclude Include="..\include\StGLMesh\StGLUVCylinder.h" />
22
<ClInclude Include="..\include\StGLMesh\StGLUVSphere.h" />
23
<ClInclude Include="..\include\StGLStereo\StFormatEnum.h" />
24
<ClInclude Include="..\include\StGLStereo\StGLProjCamera.h" />
25
26
<ClInclude Include="..\include\StImage\StImagePlane.h" />
27
<ClInclude Include="..\include\StImage\StJpegParser.h" />
28
<ClInclude Include="..\include\StImage\StPixelRGB.h" />
29
+ <ClInclude Include="..\include\StImage\StStbImage.h" />
30
<ClInclude Include="..\include\StImage\StWebPImage.h" />
31
<ClInclude Include="..\include\StSettings\StEnumParam.h" />
32
<ClInclude Include="..\include\StSettings\StFloat32Param.h " />
33
sview-20_08.tar.gz/StShared/StStbImage.cpp
Added
149
1
2
+/**
3
+ * Copyright © 2019 Kirill Gavrilov <kirill@sview.ru>
4
+ *
5
+ * Distributed under the Boost Software License, Version 1.0.
6
+ * See accompanying file license-boost.txt or copy at
7
+ * http://www.boost.org/LICENSE_1_0.txt
8
+ */
9
+
10
+#include <StImage/StStbImage.h>
11
+
12
+#include <StStrings/StLogger.h>
13
+#include <StThreads/StMutex.h>
14
+#include <StFile/StFileNode.h>
15
+
16
+//#define ST_HAVE_STB_IMAGE
17
+
18
+#ifdef ST_HAVE_STB_IMAGE
19
+ #define STB_IMAGE_IMPLEMENTATION
20
+ //#define STB_IMAGE_RESIZE_IMPLEMENTATION
21
+ //#define STB_IMAGE_WRITE_IMPLEMENTATION
22
+ #define STBI_WINDOWS_UTF8
23
+ #include <stb_image.h>
24
+ //#include <stb_image_resize.h>
25
+ //#include <stb_image_write.h>
26
+
27
+namespace {
28
+
29
+ static StImagePlane::ImgFormat convertFromStbFormat(int theChannels, bool theIsHDR) {
30
+ switch(theChannels) {
31
+ case STBI_grey: return theIsHDR ? StImagePlane::ImgGrayF : StImagePlane::ImgGray;
32
+ case STBI_grey_alpha: return StImagePlane::ImgUNKNOWN;
33
+ case STBI_rgb: return theIsHDR ? StImagePlane::ImgRGBF : StImagePlane::ImgRGB;
34
+ case STBI_rgb_alpha: return theIsHDR ? StImagePlane::ImgRGBAF : StImagePlane::ImgRGBA;
35
+ }
36
+ return StImagePlane::ImgUNKNOWN;
37
+ }
38
+
39
+}
40
+
41
+#endif
42
+
43
+bool StStbImage::init() {
44
+#ifdef ST_HAVE_STB_IMAGE
45
+ return true;
46
+#else
47
+ return false;
48
+#endif
49
+}
50
+
51
+StStbImage::StStbImage()
52
+: myStbImage(NULL) {
53
+ StStbImage::init();
54
+}
55
+
56
+StStbImage::~StStbImage() {
57
+ close();
58
+}
59
+
60
+void StStbImage::close() {
61
+ if(myStbImage != NULL) {
62
+ #ifdef ST_HAVE_STB_IMAGE
63
+ stbi_image_free(myStbImage);
64
+ #endif
65
+ myStbImage = NULL;
66
+ }
67
+}
68
+
69
+bool StStbImage::loadExtra(const StString& theFilePath,
70
+ ImageType theImageType,
71
+ uint8_t* theDataPtr,
72
+ int theDataSize,
73
+ bool theIsOnlyRGB) {
74
+ (void )theIsOnlyRGB;
75
+ if(!StStbImage::init()) {
76
+ setState("STB library is not initialized");
77
+ return false;
78
+ }
79
+
80
+ // reset current data
81
+ StImage::nullify();
82
+ setState();
83
+ close();
84
+
85
+#ifdef ST_HAVE_STB_IMAGE
86
+ bool isHdr = false;
87
+ int aWidth = 0, aHeight = 0, aChannels = 0;
88
+ //stbi_set_flip_vertically_on_load(true);
89
+ if(theDataPtr != NULL) {
90
+ (void )theImageType;
91
+ //stbi_info_from_memory();
92
+ isHdr = stbi_is_hdr_from_memory((unsigned char*)theDataPtr, theDataSize) != 0;
93
+ if(isHdr) {
94
+ //myStbImage = stbi_load_16_from_memory((unsigned char*)theDataPtr, theDataSize, &aWidth, &aHeight, &aChannels, STBI_default);
95
+ myStbImage = stbi_loadf_from_memory((unsigned char*)theDataPtr, theDataSize, &aWidth, &aHeight, &aChannels, STBI_default);
96
+ } else {
97
+ myStbImage = stbi_load_from_memory((unsigned char*)theDataPtr, theDataSize, &aWidth, &aHeight, &aChannels, STBI_default);
98
+ }
99
+ } else {
100
+ //stbi_info();
101
+ isHdr = stbi_is_hdr(theFilePath.toCString()) != 0;
102
+ if(isHdr) {
103
+ //myStbImage = stbi_load_16(theFilePath.toCString(), &aWidth, &aHeight, &aChannels, STBI_default);
104
+ myStbImage = stbi_loadf(theFilePath.toCString(), &aWidth, &aHeight, &aChannels, STBI_default);
105
+ } else {
106
+ myStbImage = stbi_load(theFilePath.toCString(), &aWidth, &aHeight, &aChannels, STBI_default);
107
+ }
108
+ }
109
+
110
+ if(myStbImage == NULL
111
+ || aWidth < 1
112
+ || aHeight < 1) {
113
+ //stbi_failure_reason()
114
+ setState("STB library, unable to load image");
115
+ close();
116
+ return false;
117
+ }
118
+
119
+ StImagePlane::ImgFormat anImgFormat = convertFromStbFormat(aChannels, isHdr);
120
+ if(anImgFormat == StImagePlane::ImgUNKNOWN) {
121
+ setState("STB library, unknown pixel format");
122
+ close();
123
+ return false;
124
+ }
125
+
126
+ setColorModelPacked(anImgFormat);
127
+ changePlane(0).initWrapper(anImgFormat, (unsigned char* )myStbImage, aWidth, aHeight);
128
+
129
+ // set debug information
130
+ StString aDummy, aFileName;
131
+ StFileNode::getFolderAndFile(theFilePath, aDummy, aFileName);
132
+ setState(StString("STB library, loaded image '") + aFileName + "' " + getDescription());
133
+ return true;
134
+#else
135
+ (void )theFilePath;
136
+ (void )theImageType;
137
+ (void )theDataPtr;
138
+ (void )theDataSize;
139
+ return false;
140
+#endif
141
+}
142
+
143
+bool StStbImage::save(const StString& ,
144
+ ImageType ,
145
+ StFormat ) {
146
+ setState("STB library, save operation is NOT implemented");
147
+ return false;
148
+}
149
sview-17_04.tar.gz/StShared/StThread.cpp -> sview-20_08.tar.gz/StShared/StThread.cpp
Changed
57
1
2
/**
3
- * Copyright © 2009-2014 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2009-2017 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* Distributed under the Boost Software License, Version 1.0.
7
* See accompanying file license-boost.txt or copy at
8
9
}
10
11
bool StThread::wait() {
12
+ if(!isValid()) {
13
+ return false;
14
+ }
15
+
16
#ifdef _WIN32
17
- return isValid() && (WaitForSingleObject((HANDLE )myThread, INFINITE) != WAIT_FAILED);
18
+ if(WaitForSingleObject((HANDLE )myThread, INFINITE) == WAIT_FAILED) {
19
+ return false;
20
+ }
21
+ CloseHandle((HANDLE )myThread);
22
+ myThread = NULL;
23
#else
24
- return isValid() && (pthread_join(myThread, NULL) == 0);
25
+ if(pthread_join(myThread, NULL) != 0) {
26
+ return false;
27
+ }
28
+ myHasHandle = false;
29
#endif
30
+ return true;
31
}
32
33
bool StThread::wait(const int theTimeMilliseconds) {
34
+ if(!isValid()) {
35
+ return false;
36
+ }
37
+
38
#ifdef _WIN32
39
- return isValid() && (WaitForSingleObject((HANDLE )myThread, (DWORD )theTimeMilliseconds) != WAIT_TIMEOUT);
40
+ if(WaitForSingleObject((HANDLE )myThread, (DWORD )theTimeMilliseconds) == WAIT_TIMEOUT) {
41
+ return false;
42
+ }
43
+ CloseHandle((HANDLE )myThread);
44
+ myThread = NULL;
45
#else
46
(void )theTimeMilliseconds;
47
- return isValid() && (pthread_join(myThread, NULL) == 0);
48
+ if(pthread_join(myThread, NULL) != 0) {
49
+ return false;
50
+ }
51
+ myHasHandle = false;
52
#endif
53
+ return true;
54
}
55
56
void StThread::kill() {
57
sview-17_04.tar.gz/StShared/StTranslations.cpp -> sview-20_08.tar.gz/StShared/StTranslations.cpp
Changed
34
1
2
params.language->changeValues().add("English");
3
myLangFolderList.add("English");
4
}
5
+ if(myResMgr->isResourceExist(StString("lang" ST_FILE_SPLITTER "Spanish" ST_FILE_SPLITTER) + myModuleName + StTranslations::DEFAULT_SUFFIX)) {
6
+ params.language->changeValues().add("Español");
7
+ myLangFolderList.add("Spanish");
8
+ }
9
if(myResMgr->isResourceExist(StString("lang" ST_FILE_SPLITTER "Russian" ST_FILE_SPLITTER) + myModuleName + StTranslations::DEFAULT_SUFFIX)) {
10
params.language->changeValues().add("русский");
11
myLangFolderList.add("Russian");
12
13
params.language->setValue(int32_t(anIdInList));
14
isLangSet = true;
15
}
16
+ } else if(aLang.isEqualsIgnoreCase(stCString("es"))) {
17
+ if(myLangFolderList.contains(stCString("Spanish"), anIdInList)
18
+ || myLangFolderList.contains(stCString("Español"), anIdInList)) {
19
+ params.language->setValue(int32_t(anIdInList));
20
+ isLangSet = true;
21
+ }
22
} else if(aLang.isEqualsIgnoreCase(stCString("fr"))) {
23
if(myLangFolderList.contains(stCString("French"), anIdInList)
24
|| myLangFolderList.contains(stCString("français"), anIdInList)) {
25
26
const StString& aLang = params.language->getValues()[theNewLang];
27
if(aLang == stCString("русский")) {
28
myLangCode = "rus";
29
+ } else if(aLang == stCString("Español")) {
30
+ myLangCode = "spa";
31
} else if(aLang == stCString("français")) {
32
myLangCode = "fre";
33
//myLangCode = "fra";
34
sview-17_04.tar.gz/StShared/StVirtualKeys.cpp -> sview-20_08.tar.gz/StShared/StVirtualKeys.cpp
Changed
28
1
2
/**
3
- * Copyright © 2013-2015 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2013-2020 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* Distributed under the Boost Software License, Version 1.0.
7
* See accompanying file license-boost.txt or copy at
8
9
stCString(","), // ST_VK_COMMA
10
stCString("-"), // ST_VK_OEM_MINUS
11
stCString("."), // ST_VK_PERIOD
12
- stCString(""), // ST_VK_OEM_2
13
- stCString(""), // ST_VK_OEM_3
14
+ stCString("/"), // ST_VK_SLASH
15
+ stCString("~"), // ST_VK_TILDE
16
stCString(""), // 193
17
stCString(""), // 194
18
stCString(""), // 195
19
20
aStr += "Fn+";
21
}
22
if(aKey == 0
23
- || aKey > 255) {
24
+ || aKey >= ST_VK_NB) {
25
return "";
26
}
27
if(aKey == ST_VK_SHIFT
28
sview-17_04.tar.gz/StShared/StWebPImage.cpp -> sview-20_08.tar.gz/StShared/StWebPImage.cpp
Changed
37
1
2
VP8_STATUS_NOT_ENOUGH_DATA
3
} VP8StatusCode;
4
5
+#ifdef ST_HAVE_WEBP
6
static const char* const WebPStatusMessages[] = {
7
"OK", // VP8_STATUS_OK
8
"OUT_OF_MEMORY", // VP8_STATUS_OUT_OF_MEMORY
9
10
"USER_ABORT", // VP8_STATUS_USER_ABORT
11
"NOT_ENOUGH_DATA" // VP8_STATUS_NOT_ENOUGH_DATA
12
};
13
+#endif
14
15
extern int WebPInitDecoderConfigInternal(StWebPImage::WebPDecoderConfig* theConfig, int theVersion);
16
17
18
}
19
20
StWebPImage::StWebPImage()
21
-: StImageFile(),
22
- myIsCompat(false) {
23
+: myIsCompat(false) {
24
#ifdef ST_HAVE_WEBP
25
myIsCompat = WebPInitDecoderConfig(&myConfig) != 0;
26
#endif
27
28
if(myIsCompat) {
29
WebPFreeDecBuffer(&myConfig.output);
30
}
31
+#else
32
+ (void )myConfig;
33
+ (void )myIsCompat;
34
#endif
35
}
36
37
sview-17_04.tar.gz/StShared/stAV.cpp -> sview-20_08.tar.gz/StShared/stAV.cpp
Changed
185
1
2
/**
3
- * Copyright © 2011-2016 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2011-2020 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* Distributed under the Boost Software License, Version 1.0.
7
* See accompanying file license-boost.txt or copy at
8
9
#endif
10
#endif
11
12
-#if(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(52, 30, 0))
13
+#if(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(52, 30, 0)) \
14
+&& ((LIBAVCODEC_VERSION_INT < AV_VERSION_INT(58, 9, 100)) || defined(ST_LIBAV_FORK))
15
class StFFMpegLocker {
16
17
public:
18
19
#endif
20
const AVPixelFormat stAV::PIX_FMT::NONE = AVPixelFormat(-1);
21
const AVPixelFormat stAV::PIX_FMT::YUV420P = AVPixelFormat( 0);
22
+const AVPixelFormat stAV::PIX_FMT::YUVA420P = ST_AV_GETPIXFMT("yuva420p");
23
const AVPixelFormat stAV::PIX_FMT::PAL8 = ST_AV_GETPIXFMT("pal8");
24
const AVPixelFormat stAV::PIX_FMT::GRAY8 = ST_AV_GETPIXFMT("gray");
25
const AVPixelFormat stAV::PIX_FMT::GRAY16 = ST_AV_GETPIXFMT("gray16");
26
const AVPixelFormat stAV::PIX_FMT::YUV422P = ST_AV_GETPIXFMT("yuv422p");
27
+const AVPixelFormat stAV::PIX_FMT::YUVA422P = ST_AV_GETPIXFMT("yuva422p");
28
const AVPixelFormat stAV::PIX_FMT::YUV444P = ST_AV_GETPIXFMT("yuv444p");
29
+const AVPixelFormat stAV::PIX_FMT::YUVA444P = ST_AV_GETPIXFMT("yuva444p");
30
const AVPixelFormat stAV::PIX_FMT::YUV410P = ST_AV_GETPIXFMT("yuv410p");
31
const AVPixelFormat stAV::PIX_FMT::YUV411P = ST_AV_GETPIXFMT("yuv411p");
32
const AVPixelFormat stAV::PIX_FMT::YUV440P = ST_AV_GETPIXFMT("yuv440p");
33
34
const AVPixelFormat stAV::PIX_FMT::BGRA64 = ST_AV_GETPIXFMT("bgra64");
35
const AVPixelFormat stAV::PIX_FMT::XYZ12 = ST_AV_GETPIXFMT("xyz12");
36
const AVPixelFormat stAV::PIX_FMT::DXVA2_VLD = ST_AV_GETPIXFMT("dxva2_vld");
37
+const AVPixelFormat stAV::PIX_FMT::VIDEOTOOLBOX_VLD = ST_AV_GETPIXFMT("videotoolbox_vld");
38
39
// TODO (Kirill Gavrilov#9) remove this stuff
40
namespace {
41
42
return stCString("none");
43
} else if(theFrmt == stAV::PIX_FMT::YUV420P) {
44
return stCString("yuv420p");
45
+ } else if(theFrmt == stAV::PIX_FMT::YUVA420P) {
46
+ return stCString("yuva420p");
47
} else if(theFrmt == stAV::PIX_FMT::PAL8) {
48
return stCString("pal8");
49
} else if(theFrmt == stAV::PIX_FMT::GRAY8) {
50
51
return stCString("gray16");
52
} else if(theFrmt == stAV::PIX_FMT::YUV422P) {
53
return stCString("yuv422p");
54
+ } else if(theFrmt == stAV::PIX_FMT::YUVA422P) {
55
+ return stCString("yuva422p");
56
} else if(theFrmt == stAV::PIX_FMT::YUV444P) {
57
return stCString("yuv444p");
58
+ } else if(theFrmt == stAV::PIX_FMT::YUVA444P) {
59
+ return stCString("yuva444p");
60
} else if(theFrmt == stAV::PIX_FMT::YUV410P) {
61
return stCString("yuv410p");
62
} else if(theFrmt == stAV::PIX_FMT::YUV411P) {
63
64
#endif
65
66
static bool initOnce() {
67
+ #if(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(52, 30, 0)) \
68
+ && ((LIBAVCODEC_VERSION_INT < AV_VERSION_INT(58, 9, 100)) || defined(ST_LIBAV_FORK))
69
// register own mutex to prevent multithreading errors
70
// while using FFmpeg functions
71
- #if(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(52, 30, 0))
72
stFFMpegLocker.init();
73
- #else
74
- #warning Ancient FFmpeg used, initialization performed in thread-unsafe manner!
75
#endif
76
+
77
+ #if(LIBAVFORMAT_VERSION_INT < AV_VERSION_INT(58, 9, 100)) || defined(ST_LIBAV_FORK)
78
// Notice, this call is absolutely not thread safe!
79
// you should never call it first time from concurrent threads.
80
// But after first initialization is done this is safe to call it anyhow
81
av_register_all();
82
+ #endif
83
+
84
#if(LIBAVFORMAT_VERSION_INT >= AV_VERSION_INT(53, 13, 0))
85
avformat_network_init();
86
#endif
87
88
89
bool stAV::isFormatYUVPlanar(const AVCodecContext* theCtx) {
90
return theCtx->pix_fmt == stAV::PIX_FMT::YUV420P
91
+ || theCtx->pix_fmt == stAV::PIX_FMT::YUVA420P
92
|| theCtx->pix_fmt == stAV::PIX_FMT::YUVJ420P
93
|| theCtx->pix_fmt == stAV::PIX_FMT::YUV422P
94
+ || theCtx->pix_fmt == stAV::PIX_FMT::YUVA422P
95
|| theCtx->pix_fmt == stAV::PIX_FMT::YUVJ422P
96
|| theCtx->pix_fmt == stAV::PIX_FMT::YUV444P
97
+ || theCtx->pix_fmt == stAV::PIX_FMT::YUVA444P
98
|| theCtx->pix_fmt == stAV::PIX_FMT::YUVJ444P
99
|| theCtx->pix_fmt == stAV::PIX_FMT::YUV440P
100
|| theCtx->pix_fmt == stAV::PIX_FMT::YUVJ440P
101
102
if(thePixFmt == stAV::PIX_FMT::NONE) {
103
return false;
104
} else if(thePixFmt == stAV::PIX_FMT::YUV420P
105
+ || thePixFmt == stAV::PIX_FMT::YUVA420P
106
|| thePixFmt == stAV::PIX_FMT::YUVJ420P
107
|| thePixFmt == stAV::PIX_FMT::YUV420P9
108
|| thePixFmt == stAV::PIX_FMT::YUV420P10
109
110
theDims.widthU = theDims.widthV = theDims.widthY / 2;
111
theDims.heightU = theDims.heightV = theDims.heightY / 2;
112
theDims.isFullScale = (thePixFmt == stAV::PIX_FMT::YUVJ420P);
113
+ theDims.hasAlpha = thePixFmt == stAV::PIX_FMT::YUVA420P;
114
} else if(thePixFmt == stAV::PIX_FMT::YUV422P
115
+ || thePixFmt == stAV::PIX_FMT::YUVA422P
116
|| thePixFmt == stAV::PIX_FMT::YUVJ422P
117
|| thePixFmt == stAV::PIX_FMT::YUV422P9
118
|| thePixFmt == stAV::PIX_FMT::YUV422P10
119
120
theDims.heightY = theDims.heightU = theDims.heightV = theHeight;
121
theDims.widthU = theDims.widthV = theDims.widthY / 2;
122
theDims.isFullScale = (thePixFmt == stAV::PIX_FMT::YUVJ422P);
123
+ theDims.hasAlpha = false;
124
} else if(thePixFmt == stAV::PIX_FMT::YUV444P
125
+ || thePixFmt == stAV::PIX_FMT::YUVA444P
126
|| thePixFmt == stAV::PIX_FMT::YUVJ444P
127
|| thePixFmt == stAV::PIX_FMT::YUV444P9
128
|| thePixFmt == stAV::PIX_FMT::YUV444P10
129
130
theDims.widthY = theDims.widthU = theDims.widthV = theWidth;
131
theDims.heightY = theDims.heightU = theDims.heightV = theHeight;
132
theDims.isFullScale = (thePixFmt == stAV::PIX_FMT::YUVJ444P);
133
+ theDims.hasAlpha = false;
134
} else if(thePixFmt == stAV::PIX_FMT::YUV440P
135
|| thePixFmt == stAV::PIX_FMT::YUVJ440P) {
136
theDims.widthY = theDims.widthU = theDims.widthV = theWidth;
137
theDims.heightY = theHeight;
138
theDims.heightU = theDims.heightV = theDims.heightY / 2;
139
theDims.isFullScale = (thePixFmt == stAV::PIX_FMT::YUVJ440P);
140
+ theDims.hasAlpha = false;
141
} else if(thePixFmt == stAV::PIX_FMT::YUV411P) {
142
theDims.widthY = theDims.widthU = theDims.widthV = theWidth;
143
theDims.heightY = theDims.heightU = theDims.heightV = theHeight;
144
theDims.widthU = theDims.widthV = theDims.widthY / 4;
145
theDims.isFullScale = false;
146
+ theDims.hasAlpha = false;
147
} else if(thePixFmt == stAV::PIX_FMT::YUV410P) {
148
theDims.widthY = theDims.widthU = theDims.widthV = theWidth;
149
theDims.heightY = theHeight;
150
theDims.widthU = theDims.widthV = theDims.widthY / 4;
151
theDims.heightU = theDims.heightV = theDims.heightY / 4;
152
theDims.isFullScale = false;
153
+ theDims.hasAlpha = false;
154
} else {
155
return false;
156
}
157
158
}
159
160
stAV::meta::Dict* stAV::meta::getFrameMetadata(AVFrame* theFrame) {
161
-#if(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(54, 38, 100)) && !defined(ST_LIBAV_FORK)
162
+#if(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(57, 81, 102)) && !defined(ST_LIBAV_FORK)
163
+ return theFrame->metadata;
164
+#elif(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(54, 38, 100)) && !defined(ST_LIBAV_FORK)
165
return av_frame_get_metadata(theFrame);
166
#else
167
return NULL;
168
169
#endif
170
}
171
172
+bool stAV::isEnabledInputProtocol(const StString& theProtocol) {
173
+ void* anOpaque = NULL;
174
+ for(const char* aName = avio_enum_protocols(&anOpaque, 0); aName != NULL; aName = avio_enum_protocols(&anOpaque, 0)) {
175
+ if(stAreEqual(theProtocol.toCString(), aName, theProtocol.Size + 1)) {
176
+ return true;
177
+ }
178
+ }
179
+ return false;
180
+}
181
+
182
StString stAV::getVersionInfo() {
183
#if(LIBAVCODEC_VERSION_INT >= AV_VERSION_INT(57, 24, 0))
184
return av_version_info();
185
sview-17_04.tar.gz/contentiousIntegration/build_sview_android.sh -> sview-20_08.tar.gz/contentiousIntegration/build_sview_android.sh
Changed
8
1
2
3
# perform building itself
4
make --directory=$aScriptPath/.. clean
5
-make --directory=$aScriptPath/.. -j $aNbJobs android ANDROID_NDK=$SVIEW_NDK FFMPEG_ROOT=$SVIEW_FFMPEG FREETYPE_ROOT=$SVIEW_FREETYPE OPENAL_ROOT=$SVIEW_OPENAL LIBCONFIG_ROOT=$SVIEW_LIBCONFIG
6
+make --directory=$aScriptPath/.. -j $aNbJobs android ANDROID_NDK=$SVIEW_NDK ANDROID_BUILD_TOOLS=$SVIEW_BUILD_TOOLS ANDROID_PLATFORM=$SVIEW_PLATFORM \
7
+ FFMPEG_ROOT=$SVIEW_FFMPEG FREETYPE_ROOT=$SVIEW_FREETYPE OPENAL_ROOT=$SVIEW_OPENAL LIBCONFIG_ROOT=$SVIEW_LIBCONFIG WERROR_LEVEL=1
8
sview-17_04.tar.gz/contentiousIntegration/build_sview_linux.sh -> sview-20_08.tar.gz/contentiousIntegration/build_sview_linux.sh
Changed
7
1
2
3
# perform building itself
4
make --directory=$aScriptPath/.. clean
5
-make --directory=$aScriptPath/.. -j $aNbJobs
6
+make --directory=$aScriptPath/.. -j $aNbJobs WERROR_LEVEL=1
7
sview-17_04.tar.gz/contentiousIntegration/build_sview_osx.sh -> sview-20_08.tar.gz/contentiousIntegration/build_sview_osx.sh
Changed
7
1
2
3
# perform building itself
4
make --directory=$aScriptPath/.. clean
5
-make --directory=$aScriptPath/.. -j $aNbJobs
6
+make --directory=$aScriptPath/.. -j $aNbJobs WERROR_LEVEL=1
7
sview-17_04.tar.gz/copy_res.bat -> sview-20_08.tar.gz/copy_res.bat
Changed
17
1
2
chcp 65001
3
4
if not exist "%TARGET_OUTPUT_DIR%lang\English" mkdir "%TARGET_OUTPUT_DIR%lang\English"
5
+if not exist "%TARGET_OUTPUT_DIR%lang\Español" mkdir "%TARGET_OUTPUT_DIR%lang\Español"
6
if not exist "%TARGET_OUTPUT_DIR%lang\русский" mkdir "%TARGET_OUTPUT_DIR%lang\русский"
7
if not exist "%TARGET_OUTPUT_DIR%lang\français" mkdir "%TARGET_OUTPUT_DIR%lang\français"
8
if not exist "%TARGET_OUTPUT_DIR%lang\Deutsch" mkdir "%TARGET_OUTPUT_DIR%lang\Deutsch"
9
10
if not exist "%TARGET_OUTPUT_DIR%lang\Czech" mkdir "%TARGET_OUTPUT_DIR%lang\Czech"
11
12
copy /Y lang\english\* "%TARGET_OUTPUT_DIR%lang\English\"
13
+copy /Y lang\spanish\* "%TARGET_OUTPUT_DIR%lang\Español\"
14
copy /Y lang\russian\* "%TARGET_OUTPUT_DIR%lang\русский\"
15
copy /Y lang\french\* "%TARGET_OUTPUT_DIR%lang\français\"
16
copy /Y lang\german\* "%TARGET_OUTPUT_DIR%lang\Deutsch\"
17
sview-17_04.tar.gz/copy_res.sh -> sview-20_08.tar.gz/copy_res.sh
Changed
17
1
2
PROJECT_NAME=$2
3
4
mkdir -p "${TARGET_OUTPUT_DIR}lang/English/"
5
+mkdir -p "${TARGET_OUTPUT_DIR}lang/Español/"
6
mkdir -p "${TARGET_OUTPUT_DIR}lang/русский/"
7
mkdir -p "${TARGET_OUTPUT_DIR}lang/français/"
8
mkdir -p "${TARGET_OUTPUT_DIR}lang/Deutsch/"
9
10
mkdir -p "${TARGET_OUTPUT_DIR}lang/Korean/"
11
mkdir -p "${TARGET_OUTPUT_DIR}lang/Czech/"
12
cp -f -r lang/english/* "${TARGET_OUTPUT_DIR}lang/English/"
13
+cp -f -r lang/spanish/* "${TARGET_OUTPUT_DIR}lang/Español/"
14
cp -f -r lang/russian/* "${TARGET_OUTPUT_DIR}lang/русский/"
15
cp -f -r lang/french/* "${TARGET_OUTPUT_DIR}lang/français/"
16
cp -f -r lang/german/* "${TARGET_OUTPUT_DIR}lang/Deutsch/"
17
sview-17_04.tar.gz/debian/changelog.tmpl -> sview-20_08.tar.gz/debian/changelog.tmpl
Changed
55
1
2
3
-- Kirill Gavrilov <kirill@sview.ru> unknown_date
4
5
+sview (1:20.05-1~unknown_distrib) unknown_distrib; urgency=low
6
+
7
+ + Added Spanish translation files.
8
+ + Image Viewer - added trilinear texture filtering option generating mip-maps.
9
+ + Image Viewer - support 1x6 cubemap layout.
10
+ + Image Viewer - panorama is now automatically enabled for JPEG files with GPano:ProjectionType tag.
11
+ + Image Viewer - panorama is now automatically enabled for JPEG files with 360Stereo/360Mono tags (game screenshots).
12
+ + Image Viewer - support DDS-packed cubemaps.
13
+ + Movie Player - image-based subtitles size can be now adjusted.
14
+ * Movie Player - workaround subtitles seeking issues for attached SRT files.
15
+ * Movie Player - fixed ASS subtitles formatting issue on files without closure tags.
16
+ * Movie Player - added handling of image-based subtitles encoded as stereoscopic pair (side-by-side).
17
+ * Image Viewer - fixed poor quality on saving JPEG (yuv420p) image into PNG (rgb).
18
+ * Image Viewer - fixed displaying WebP images with alpha channel (yuva pixel formats).
19
+ * fontconfig library is now used to retrieve paths to system fonts on Linux.
20
+
21
+ -- Kirill Gavrilov <kirill@sview.ru> Wed, 20 May 2020 15:25:33 +0300
22
+
23
+sview (1:19.08-2~unknown_distrib) unknown_distrib; urgency=low
24
+
25
+ + Support VR180 hemisphere and cylindrical panorama inputs.
26
+ * Minor corrections/improvements.
27
+
28
+ -- Kirill Gavrilov <kirill@sview.ru> Sun, 04 Aug 2019 20:00:00 +0300
29
+
30
+sview (17.10-1~unknown_distrib) unknown_distrib; urgency=low
31
+
32
+ + Image Viewer - display Slideshow delay parameter in Settings dialog.
33
+ + Movie Player - add general information about the stream (bitrate, codec, PAR, DAR) in File Info dialog.
34
+ * Movie Player - fix seeking to the very beginning of the file.
35
+ * Movie Player - fix (workaround) displaying attached image within some mp3 files.
36
+ * Fix text rendering artifacts when using glyphs with kerning defined.
37
+ * Fix compilation on glibc 2.26+ (Ubuntu 17.10+)
38
+
39
+ -- Kirill Gavrilov <kirill@sview.ru> Mon, 23 Oct 2017 22:29:34 +0300
40
+
41
+sview (17.04-1~unknown_distrib) unknown_distrib; urgency=low
42
+
43
+ + Movie Player - add audio positioning while playing spheric panorama video.
44
+ + Movie Player - handle rotation info stored within video stream.
45
+ + Image Viewer, Movie Player - add overlay control for adjusting image color
46
+ + Movie Player - add option to force HRTF mixing in OpenAL Soft.
47
+ * Fix saving PNG images when using up-to-date FFmpeg.
48
+ * Image Viewer, Movie Player - fix too slow opening File Info dialog in case of long metadata.
49
+
50
+ -- Kirill Gavrilov <kirill@sview.ru> Sun, 16 Apr 2017 21:45:20 +0300
51
+
52
sview (16.04-1~unknown_distrib) unknown_distrib; urgency=low
53
54
+ Movie Player - implement GPU-accelerated conversion of NV12 and XYZ12 formats.
55
sview-17_04.tar.gz/debian/control -> sview-20_08.tar.gz/debian/control
Changed
10
1
2
Section: contrib/video
3
Priority: extra
4
Maintainer: Kirill Gavrilov <kirill@sview.ru>
5
-Build-Depends: debhelper (>= 7.0.50~), g++ (>= 4.0), libopenal-dev, libgl1-mesa-dev | libgl-dev, libgtk2.0-dev, libxpm-dev, libavcodec-dev, libavdevice-dev, libavformat-dev, libavutil-dev, libswscale-dev, libconfig++8-dev, libconfig8-dev, libfreetype6-dev, libxpm-dev
6
+Build-Depends: debhelper (>= 7.0.50~), g++ (>= 4.0), libopenal-dev, libgl1-mesa-dev | libgl-dev, libgtk2.0-dev, libxpm-dev, libavcodec-dev, libavdevice-dev, libavformat-dev, libavutil-dev, libswscale-dev, libconfig++-dev, libfreetype6-dev, libxpm-dev
7
Standards-Version: 3.9.1
8
Homepage: http://www.sview.ru
9
10
sview-17_04.tar.gz/debian/copyright -> sview-20_08.tar.gz/debian/copyright
Changed
10
1
2
Source: <http://www.sview.ru>
3
4
Files: *
5
-Copyright: 2008-2015 Kirill Gavrilov <kirill@sview.ru>
6
+Copyright: 2008-2020 Kirill Gavrilov <kirill@sview.ru>
7
License: GPL-3.0+
8
9
Files: debian/*
10
sview-17_04.tar.gz/distribution/build.bat -> sview-20_08.tar.gz/distribution/build.bat
Changed
79
1
2
3
if exist "%~dp0env.bat" call "%~dp0env.bat"
4
5
-set YEAR=%date:~-2,4%
6
-set MONTH00=%date:~-7,2%
7
-set MONTH=%date:~-7,2%
8
-set DAY=%date:~0,2%
9
-
10
-rem Remove first zero
11
-if "%MONTH%"=="01" set MONTH=1
12
-if "%MONTH%"=="02" set MONTH=2
13
-if "%MONTH%"=="03" set MONTH=3
14
-if "%MONTH%"=="04" set MONTH=4
15
-if "%MONTH%"=="05" set MONTH=5
16
-if "%MONTH%"=="06" set MONTH=6
17
-if "%MONTH%"=="07" set MONTH=7
18
-if "%MONTH%"=="08" set MONTH=8
19
-if "%MONTH%"=="09" set MONTH=9
20
-
21
-if "%DAY%"=="01" set DAY=1
22
-if "%DAY%"=="02" set DAY=2
23
-if "%DAY%"=="03" set DAY=3
24
-if "%DAY%"=="04" set DAY=4
25
-if "%DAY%"=="05" set DAY=5
26
-if "%DAY%"=="06" set DAY=6
27
-if "%DAY%"=="07" set DAY=7
28
-if "%DAY%"=="08" set DAY=8
29
-if "%DAY%"=="09" set DAY=9
30
+for /F "skip=1 delims=" %%F in ('
31
+ wmic PATH Win32_LocalTime GET Day^,Month^,Year /FORMAT:TABLE
32
+') do (
33
+ for /F "tokens=1-3" %%L in ("%%F") do (
34
+ set DAY=%%L
35
+ set DAY00=0%%L
36
+ set MONTH=%%M
37
+ set MONTH00=0%%M
38
+ set YEAR=%%N
39
+ )
40
+)
41
+set YEAR=%YEAR:~-2,4%
42
43
set SVIEW_DISTR_PATH_X86=%~dp0temp\sView-win-x86
44
set SVIEW_DISTR_PATH_AMD64=%~dp0temp\sView-win-amd64
45
46
47
rem Activate experimental WebP support
48
echo #define ST_HAVE_WEBP>> "%SVIEW_BUILD_CONF%"
49
+rem Activate notifications about sView updates available on sview.ru
50
+echo #define ST_UPDATES_CHECK>> "%SVIEW_BUILD_CONF%"
51
52
rem Create configuration for InnoSetup build script
53
echo #define SVIEW_VER "%YEAR%.%MONTH%.%SVIEW_VER_TYPE_NUM%.%DAY%"> config.iss
54
55
echo Perform rebuild MSVC x86
56
rem www.codeblocks.org
57
rem --multiple-instance
58
-start /WAIT /D "%CB_PATH%" codeblocks.exe --rebuild --target="WIN_vc_x86" "%~dp0..\workspace.workspace"
59
+start /WAIT /D "%CB_PATH%" codeblocks.exe --rebuild --target="WIN_vc_x86" "%~dp0..\workspace.workspace"
60
+if errorlevel 1 (
61
+ move /Y ..\include\stconfig.conf.buildbak ..\include\stconfig.conf
62
+ echo Build FAILED
63
+ pause
64
+ exit /B
65
+ goto :eof
66
+)
67
echo Perform rebuild MSVC x86_64
68
start /WAIT /D "%CB_PATH%" codeblocks.exe --rebuild --target="WIN_vc_AMD64" "%~dp0..\workspace.workspace"
69
+if errorlevel 1 (
70
+ move /Y ..\include\stconfig.conf.buildbak ..\include\stconfig.conf
71
+ echo Build FAILED
72
+ pause
73
+ exit /B
74
+ goto :eof
75
+)
76
77
rem move default config file back
78
move /Y ..\include\stconfig.conf.buildbak ..\include\stconfig.conf
79
sview-17_04.tar.gz/distribution/build.iss -> sview-20_08.tar.gz/distribution/build.iss
Changed
122
1
2
SetupIconFile=media\sView_Setup.ico
3
WizardImageFile=media\sView_WizImage.bmp
4
WizardSmallImageFile=media\sView_WizImageSmall.bmp
5
+UninstallDisplayIcon={app}\{#SVIEW_EXE_NAME}
6
; Additional requirements
7
ChangesAssociations=true
8
ChangesEnvironment=true
9
10
;InfoBeforeFile: {#SVIEW_DISTR_PATH_x86}\info\ReadMeEn.rtf
11
Name: english; MessagesFile: compiler:Default.isl; LicenseFile: {#SVIEW_DISTR_PATH_x86}\info\license.rtf
12
Name: russian; MessagesFile: compiler:Languages\Russian.isl; LicenseFile: {#SVIEW_DISTR_PATH_x86}\info\license.rtf
13
+Name: spanish; MessagesFile: compiler:Languages\Spanish.isl; LicenseFile: {#SVIEW_DISTR_PATH_x86}\info\license.rtf
14
Name: french; MessagesFile: compiler:Languages\French.isl; LicenseFile: {#SVIEW_DISTR_PATH_x86}\info\license.rtf
15
Name: german; MessagesFile: compiler:Languages\German.isl; LicenseFile: {#SVIEW_DISTR_PATH_x86}\info\license.rtf
16
Name: korean; MessagesFile: compiler:Languages\Korean.isl; LicenseFile: {#SVIEW_DISTR_PATH_x86}\info\license.rtf
17
18
; Installation types
19
english.FullInstallation=Full Installation
20
russian.FullInstallation=Полная установка
21
+spanish.FullInstallation=Instalación completa
22
french.FullInstallation=Installation complète
23
german.FullInstallation=Vollständige Installation
24
korean.FullInstallation=전체 설치
25
chinese.FullInstallation=全部安装
26
english.CustomInstallation=Custom Installation
27
+spanish.CustomInstallation=Instalación personalizada
28
russian.CustomInstallation=Выборочная установка
29
french.CustomInstallation=Installation personnalisée
30
german.CustomInstallation=Benutzerdefinierte Installation
31
32
chinese.CustomInstallation=自定义安装
33
; Components
34
english.StCore=Core files
35
+spanish.StCore=Archivos compartidos
36
russian.StCore=Общие файлы
37
german.StCore=Core-Dateien
38
english.StBrowserPlugins=NPAPI Browser plugin (Firefox, Google Chrome, Opera,...)
39
+spanish.StBrowserPlugins=Plugin de navegador NPAPI (Firefox, Google Chrome, Opera,...)
40
russian.StBrowserPlugins=NPAPI плагин для браузеров Firefox, Google Chrome, Opera,...
41
english.StActiveXPlugin=ActiveX control for Internet Explorer
42
+spanish.StActiveXPlugin=Control ActiveX para Internet Explorer
43
russian.StActiveXPlugin=ActiveX плагин для браузера Internet Explorer
44
english.StDrawers=Media types support
45
+spanish.StDrawers=Soporte de tipos de medios
46
russian.StDrawers=Поддержка медиа-типов
47
english.StImageViewer=Stereoscopic Image Viewer
48
+spanish.StImageViewer=Visor de imagen estereoscópica
49
russian.StImageViewer=Просмотр стереоизображений
50
english.StMoviePlayer=Stereoscopic Movie Player
51
+spanish.StMoviePlayer=Reproductor de películas estereoscópicas
52
russian.StMoviePlayer=Воспроизведение стереовидео
53
english.StRenderers=Device support
54
+spanish.StRenderers=Soporte del dispositivo
55
russian.StRenderers=Поддержка устройств стереовывода
56
german.StRenderers=Geräteunterstützung
57
english.StOutAnaglyph=Anaglyph glasses
58
+spanish.StOutAnaglyph=Gafas anaglíficas
59
russian.StOutAnaglyph=Анаглифные очки
60
german.StOutAnaglyph=Anaglyphenbrille
61
english.StOutDual=Mirror Displays, Dual Projectors
62
+spanish.StOutDual=Salida espejo, Salida dual
63
russian.StOutDual=Зеркальные системы, 2х-проекторные системы
64
english.StOutInterlace=Interlaced Displays, DLP TV
65
+spanish.StOutInterlace=Filas entrelazadas, DLP TV
66
russian.StOutInterlace=Чересстрочные мониторы, DLP ТВ
67
english.StOutIZ3D=IZ3D Display
68
+spanish.StOutIZ3D=Visualización IZ3D
69
russian.StOutIZ3D=Монитор IZ3D
70
german.StOutIZ3D=iZ3D-Bildschirmen
71
english.StOutPageFlip=Shutter glasses
72
+spanish.StOutPageFlip=Gafas de obturador
73
russian.StOutPageFlip=Затворные очки
74
german.StOutPageFlip=Shutterbrille
75
english.StOutDistorted=Distorted output
76
+spanish.StOutDistorted=Salida distorsionada
77
russian.StOutDistorted=Искажённый вывод
78
; File associations
79
english.FileAssociations=File associations
80
+spanish.FileAssociations=Asociaciones de archivos
81
russian.FileAssociations=Файловые ассоциации
82
german.FileAssociations=Dateizuordnungen
83
english.AssocStereoImages=Associate stereoscopic images with sView (*.jps; *.pns; *.mpo)
84
+spanish.AssocStereoImages=Asociar imágenes estereoscópicas con sView (*.jps; *.pns; *.mpo)
85
russian.AssocStereoImages=Связать с sView стереоизображения (*.jps; *.pns; *.mpo)
86
german.AssocStereoImages=Associate stereoskopische Bilder mit sView (*.jps; *.pns; *.mpo)
87
english.AssocImages=Associate common images with sView (*.jpg; *.png; *.webp; *.bmp; *.exr; *.hdr; *.tga)
88
+spanish.AssocImages=Asociar imágenes comunes con sView (*.jpg; *.png; *.webp; *.bmp; *.exr; *.hdr; *.tga)
89
russian.AssocImages=Связать с sView обычные изображения (*.jpg; *.png; *.webp; *.bmp; *.exr; *.hdr; *.tga)
90
german.AssocImages=Associate normale Bilder mit sView (*.jpg; *.png; *.webp; *.bmp; *.exr; *.hdr; *.tga)
91
english.AssocMovies=Associate video files with sView (*.avi; *.mkv; *.mk3d; *.webm; *.wmv; *.ts)
92
+spanish.AssocMovies=Asociar archivos de video con sView (*.avi; *.mkv; *.mk3d; *.webm; *.wmv; *.ts)
93
russian.AssocMovies=Связать с sView видеофайлы (*.avi; *.mkv; *.mk3d; *.webm; *.wmv; *.ts)
94
german.AssocMovies=Associate Videodateien mit sView (*.avi; *.mkv; *.mk3d; *.webm; *.wmv; *.ts)
95
english.AssocMusic=Associate music files with sView (*.mp3; *.ogg; *.wav; *.flac; *.ape)
96
+spanish.AssocMusic=Asociar archivos de música con sView (*.mp3; *.ogg; *.wav; *.flac; *.ape)
97
russian.AssocMusic=Связать с sView музыкальные файлы (*.mp3; *.ogg; *.wav; *.flac; *.ape)
98
german.AssocMusic=Associate Musikdateien mit sView (*.mp3; *.ogg; *.wav; *.flac; *.ape)
99
english.AssocPlaylists=Associate playlist files with sView (*.m3u)
100
+spanish.AssocPlaylists=Asociar archivos de lista de reproducción con sView (*.m3u)
101
; OpenAL soft
102
english.OpenALSoft51=OpenAL soft - force 5.1 channel output
103
russian.OpenALSoft51=OpenAL soft - force 5.1 channel output
104
105
Name: {group}\sView - Image Viewer; Filename: {app}\amd64\{#SVIEW_EXE_NAME}; Components: StDrawers\StImageViewer; IconFilename: {app}\amd64\{#SVIEW_EXE_NAME}; Comment: "{cm:StImageViewer}"; IconIndex: 0; Parameters: "--in=image --demo=""{app}\demo.jps"""; Check: IsWin64
106
Name: {group}\sView - Movie Player; Filename: {app}\{#SVIEW_EXE_NAME}; Components: StDrawers\StMoviePlayer; IconFilename: {app}\{#SVIEW_EXE_NAME}; Comment: "{cm:StMoviePlayer}"; IconIndex: 0; Parameters: "--in=video"; Check: not IsWin64
107
Name: {group}\sView - Movie Player; Filename: {app}\amd64\{#SVIEW_EXE_NAME}; Components: StDrawers\StMoviePlayer; IconFilename: {app}\amd64\{#SVIEW_EXE_NAME}; Comment: "{cm:StMoviePlayer}"; IconIndex: 0; Parameters: "--in=video"; Check: IsWin64
108
-Name: {group}\Extras\sView - Failsafe; Filename: {app}\{#SVIEW_EXE_NAME}; Components: StDrawers\StImageViewer and StRenderers\StOutAnaglyph; IconFilename: {app}\{#SVIEW_EXE_NAME}; Comment: Failsafe sView launch; IconIndex: 0; Parameters: --out=StOutAnaglyph --in=image
109
Name: {group}\Extras\sView - Autodetection; Filename: {app}\{#SVIEW_EXE_NAME}; Components: StDrawers\StImageViewer; IconFilename: {app}\{#SVIEW_EXE_NAME}; Comment: Failsafe sView launch; IconIndex: 0; Parameters: --out=Auto --in=image
110
-Name: {group}\Extras\sView - Movie Player 32bit; Filename: {app}\{#SVIEW_EXE_NAME}; Components: StDrawers\StMoviePlayer; IconFilename: {app}\{#SVIEW_EXE_NAME}; Comment: "{cm:StMoviePlayer}"; IconIndex: 0; Parameters: "--in=video"; Check: IsWin64
111
Name: {group}\Extras\sView - Movie Player (Last File); Filename: {app}\{#SVIEW_EXE_NAME}; Components: StDrawers\StMoviePlayer; IconFilename: {app}\{#SVIEW_EXE_NAME}; Comment: "{cm:StMoviePlayer}"; IconIndex: 0; Parameters: "--last"; Check: not IsWin64
112
Name: {group}\Extras\sView - Movie Player (Last File); Filename: {app}\amd64\{#SVIEW_EXE_NAME}; Components: StDrawers\StMoviePlayer; IconFilename: {app}\amd64\{#SVIEW_EXE_NAME}; Comment: "{cm:StMoviePlayer}"; IconIndex: 0; Parameters: "--last"; Check: IsWin64
113
Name: {group}\Extras\sView - Diagnostics; Filename: {app}\{#SVIEW_EXE_NAME}; Components: StCore; IconFilename: {app}\{#SVIEW_EXE_NAME}; Comment: sView Diagnostics; IconIndex: 0; Parameters: "--in=StDiagnostics"; Check: not IsWin64
114
115
Root: HKCU; Subkey: SOFTWARE\sView; ValueType: none; Flags: uninsdeletekey; Tasks: ; Languages: ; ValueData: sView 2011
116
Root: HKCU; Subkey: Software\sView\sView; ValueType: string; ValueName: language; ValueData: русский; Tasks: ; Languages: russian; Flags: uninsdeletekey
117
Root: HKCU; Subkey: Software\sView\sView; ValueType: string; ValueName: language; ValueData: English; Tasks: ; Languages: english; Flags: uninsdeletekey
118
+Root: HKCU; Subkey: Software\sView\sView; ValueType: string; ValueName: language; ValueData: Español; Tasks: ; Languages: spanish; Flags: uninsdeletekey
119
Root: HKCU; Subkey: Software\sView\sView; ValueType: string; ValueName: language; ValueData: français; Tasks: ; Languages: french; Flags: uninsdeletekey
120
Root: HKCU; Subkey: Software\sView\sView; ValueType: string; ValueName: language; ValueData: Deutsch; Tasks: ; Languages: german; Flags: uninsdeletekey
121
Root: HKCU; Subkey: Software\sView\sView; ValueType: string; ValueName: language; ValueData: Korean; Tasks: ; Languages: korean; Flags: uninsdeletekey
122
sview-17_04.tar.gz/distribution/buildDebSrc_ppa.sh -> sview-20_08.tar.gz/distribution/buildDebSrc_ppa.sh
Changed
55
1
2
# Ubuntu 15.10 (Wily Werewolf)
3
# Ubuntu 16.04 LTS (Xenial Xerus)
4
# Ubuntu 16.10 (Yakkety Yak)
5
-#aDistribs=("trusty" "vivid" "wily" "xenial" "yakkety")
6
-aDistribs=("vivid" "wily" "xenial")
7
+# Ubuntu 17.04 (Zesty Zapus)
8
+# Ubuntu 17.10 (Artful Aardvark)
9
+# Ubuntu 18.04 LTS (Bionic Beaver)
10
+# Ubuntu 18.10 (Cosmic Cuttlefish)
11
+# Ubuntu 19.04 (Disco Dingo)
12
+# Ubuntu 19.10
13
+# Ubuntu 20.04 LTS (Focal Fossa)
14
+# Ubuntu 20.10 (Groovy Gorilla)
15
+aDistribs=("xenial" "bionic" "focal")
16
17
# Debian
18
#aDistribs=("stable" "unstable" "testing-proposed-updates" "experimental")
19
20
# remove temporary files
21
rm -f temp/*.build
22
+rm -f temp/*.buildinfo
23
rm -f temp/*.changes
24
rm -f temp/*.dsc
25
rm -f temp/*.tar.gz
26
27
for aDistr in "${aDistribs[@]}"
28
do
29
echo "Prepare source package for '$aDistr'"
30
- sed "s/unknown_distrib/${aDistr}/g" "debian/changelog.tmpl" > "debian/changelogtmp1"
31
- sed "s/unknown_version/${aDebVersion}~${aDistr}/g" "debian/changelogtmp1" > "debian/changelogtmp2"
32
- sed "s/unknown_date/${aCurrentDate}/g" "debian/changelogtmp2" > "debian/changelog"
33
+ sed "s/unknown_distrib/${aDistr}/g" "debian/changelog.tmpl" > "debian/changelogtmp1"
34
+ sed "s/unknown_version/1:${aDebVersion}~${aDistr}/g" "debian/changelogtmp1" > "debian/changelogtmp2"
35
+ sed "s/unknown_date/${aCurrentDate}/g" "debian/changelogtmp2" > "debian/changelog"
36
rm -f debian/changelogtmp*
37
38
mkdir -p ../$aDistr
39
debuild -S
40
- mv -f ../*.build ../$aDistr
41
- mv -f ../*.changes ../$aDistr
42
- mv -f ../*.dsc ../$aDistr
43
- mv -f ../*.tar.gz ../$aDistr
44
- mv -f ../*.tar.xz ../$aDistr
45
+ mv -f ../*.build ../$aDistr
46
+ mv -f ../*.buildinfo ../$aDistr
47
+ mv -f ../*.changes ../$aDistr
48
+ mv -f ../*.dsc ../$aDistr
49
+ mv -f ../*.tar.*z ../$aDistr
50
+ #mv -f ../*.tar.gz ../$aDistr
51
+ #mv -f ../*.tar.xz ../$aDistr
52
done
53
54
#for aDistr in "${aDistribs[@]}"
55
sview-17_04.tar.gz/distribution/buildMac.sh -> sview-20_08.tar.gz/distribution/buildMac.sh
Changed
13
1
2
cp -f ../license-gpl-3.0.txt $buildRoot/sView.app/Contents/MacOS/info/license.txt
3
4
# copy sView compiled files
5
-if [ -e ../bin/MAC_gcc/build.log ]; then
6
- mv -f ../bin/MAC_gcc/build.log $buildRoot/
7
-fi
8
-cp -f -R ../bin/MAC_gcc/sView.app/* $buildRoot/sView.app/
9
+cp -f -R ../build/sView.app/* $buildRoot/sView.app/
10
11
# create symlink to Applications
12
ln -f -s /Applications "$buildRoot/"
13
sview-20_08.tar.gz/distribution/qmake
Added
2
1
+(directory)
2
sview-20_08.tar.gz/distribution/qmake/.gitignore
Added
6
1
2
+/*/*.pro
3
+/*/*/*.pro
4
+*.pro.user
5
+custom.pri
6
sview-20_08.tar.gz/distribution/qmake/custom.pri.template
Added
24
1
2
+ST_MAKE_TARGET = android
3
+ANDROID_EABI = armeabi-v7a
4
+#ANDROID_EABI = arm64-v8a
5
+#ANDROID_EABI = x86
6
+
7
+!isEmpty(ST_MAKE_TARGET) {
8
+ ST_DEPS_ROOT = $$_PRO_FILE_PWD_/../../../3rdparty/android/build
9
+
10
+ ANDROID_NDK = $$ST_DEPS_ROOT/android-ndk-r12b
11
+ ANDROID_BUILD_TOOLS = $$ST_DEPS_ROOT/android-build-tools-26.0.3
12
+ ANDROID_PLATFORM = $$ST_DEPS_ROOT/android-15.jar
13
+ FFMPEG_ROOT = $$ST_DEPS_ROOT/FFmpeg-2016-07-02-git-21ee644-arm-linux-androideabi-4.9.x-LGPL
14
+ FREETYPE_ROOT = $$ST_DEPS_ROOT/freetype-2.6.3-android
15
+ OPENAL_ROOT = $$ST_DEPS_ROOT/openal-soft-1.17.2-arm7
16
+ LIBCONFIG_ROOT = $$ST_DEPS_ROOT/libconfig-1.4.9-arm7
17
+
18
+ ANDROID_KEY_GUI = 1
19
+ #ANDROID_KEYSTORE = $$ST_DEPS_ROOT/sview_debug.key
20
+ #ANDROID_KEYSTORE_PASSWORD = 1
21
+ #ANDROID_KEY = "sview android key"
22
+ #ANDROID_KEY_PASSWORD = 2
23
+}
24
sview-20_08.tar.gz/distribution/qmake/dummy.cpp
Added
3
1
2
+int main() { return 1; }
3
sview-20_08.tar.gz/distribution/qmake/sView.pro
Added
31
1
2
+# This is a Solution project for sView.
3
+# It is intended only for code navigation using Qt Creator, not for building project!
4
+#
5
+# To use this project, open it in Qt Creator, "Run qmake" once,
6
+# close the project and open it anew, until the list of sView modules will not appear in Projects list.
7
+# Then "Run qmake" and "Build Project" which would redirect to Makefile in sView root folder.
8
+TEMPLATE = subdirs
9
+
10
+# Iterate over Modules and generate sub-projects
11
+aSolTkList = StShared StGLWidgets StCore StOutAnaglyph StOutDual StOutInterlace StOutPageFlip StOutIZ3D StOutDistorted StImageViewer StMoviePlayer StDiagnostics StCADViewer StBrowserPlugin sview StTests
12
+for (aSolToolkit, aSolTkList) {
13
+ eval(sviewtkgen_$${aSolToolkit}.input = $$_PRO_FILE_PWD_/sViewToolkit.pro.in)
14
+ eval(sviewtkgen_$${aSolToolkit}.output = $$_PRO_FILE_PWD_/$${aSolToolkit}/$${aSolToolkit}.pro)
15
+ eval(sviewkgen_$${aSolToolkit}.config = verbatim)
16
+ eval(QMAKE_SUBSTITUTES += sviewtkgen_$${aSolToolkit})
17
+ SUBDIRS += $${aSolToolkit}
18
+
19
+ !equals(aSolToolkit, StShared) {
20
+ #$${aSolToolkit}.depends += StShared
21
+ }
22
+}
23
+
24
+aTxtListTxt = $$files($$_PRO_FILE_PWD_/../../license-*.txt)
25
+aTxtListMd1 = $$files($$_PRO_FILE_PWD_/../../*.md)
26
+aTxtListMd2 = $$files($$_PRO_FILE_PWD_/../../docs/*.md)
27
+OTHER_FILES += $$aTxtListTxt
28
+OTHER_FILES += $$aTxtListMd1
29
+OTHER_FILES += $$aTxtListMd2
30
+OTHER_FILES += $$_PRO_FILE_PWD_/../../Makefile
31
sview-20_08.tar.gz/distribution/qmake/sViewToolkit.pro.in
Added
4
1
2
+ST_TOOLKIT_NAME = \$\$TARGET
3
+include(../tk.pri)
4
sview-20_08.tar.gz/distribution/qmake/tk.pri
Added
87
1
2
+# This is a project template file defining an sView Toolkit.
3
+# This project should be included with predefined ST_TOOLKIT_NAME variable.
4
+
5
+#TEMPLATE = lib
6
+TEMPLATE = aux
7
+
8
+# Disable some dummy Qt defaults
9
+QT -= core gui
10
+CONFIG -= qt app_bundle
11
+CONFIG -= debug_and_release
12
+
13
+sViewRoot = $$_PRO_FILE_PWD_/../../..
14
+DESTDIR = $$sViewRoot/build
15
+LIBS += -L$$sViewRoot/build
16
+exists(custom.pri) { include(custom.pri) }
17
+
18
+aSrcListHpp0 = $$files($$sViewRoot/$$ST_TOOLKIT_NAME/*.h, true)
19
+aSrcListHpp1 = $$files($$sViewRoot/include/$$ST_TOOLKIT_NAME/*.h)
20
+aSrcListCpp = $$files($$sViewRoot/$$ST_TOOLKIT_NAME/*.cpp, true)
21
+aSrcListMm = $$files($$sViewRoot/$$ST_TOOLKIT_NAME/*.mm, true)
22
+aSrcListJava = $$files($$sViewRoot/$$ST_TOOLKIT_NAME/*.java, true)
23
+aSrcListRc = $$files($$sViewRoot/$$ST_TOOLKIT_NAME/*.rc, true)
24
+aSrcListXml = $$files($$sViewRoot/$$ST_TOOLKIT_NAME/*.xml, true)
25
+aSrcListPlist= $$files($$sViewRoot/$$ST_TOOLKIT_NAME/*.plist, true)
26
+INCLUDEPATH += $$sViewRoot/include
27
+INCLUDEPATH += $$sViewRoot/3rdparty/include
28
+HEADERS += $$aSrcListHpp0
29
+HEADERS += $$aSrcListHpp1
30
+!equals(TEMPLATE, aux) {
31
+ SOURCES += $$aSrcListCpp
32
+ mac { SOURCES += $$aSrcListMm }
33
+}
34
+OTHER_FILES += $$aSrcListJava
35
+OTHER_FILES += $$aSrcListRc
36
+OTHER_FILES += $$aSrcListXml
37
+OTHER_FILES += $$aSrcListPlist
38
+
39
+aLngList = chinese czech english french german korean russian
40
+for (aLngIter, aLngList) {
41
+ aSrcListLng = $$files($$sViewRoot/$$ST_TOOLKIT_NAME/lang/$$aLngIter/*.lng)
42
+ OTHER_FILES += $$aSrcListLng
43
+}
44
+
45
+equals(ST_TOOLKIT_NAME, StShared) {
46
+ aSrcListHppX = $$files($$sViewRoot/include/*.h,true)
47
+ HEADERS += $$aSrcListHppX
48
+
49
+ DEFINES += ST_SHARED_DLL
50
+} else:equals(ST_TOOLKIT_NAME, sview) {
51
+ # Define sView executable which Qt Creator will automatically use for "Run".
52
+ # Touch dummy.cpp to force QMAKE_POST_LINK redirecting to main Makefile to be executed within each build.
53
+ TEMPLATE = app
54
+ mac {
55
+ TARGET = sView.app/Contents/MacOS/sView
56
+ } else {
57
+ TARGET = sView
58
+ }
59
+ SOURCES += $$_PRO_FILE_PWD_/../dummy.cpp
60
+ QMAKE_POST_LINK += rm $(TARGET); touch $$_PRO_FILE_PWD_/../dummy.cpp;
61
+
62
+ # Redirect clean to main Makefile.
63
+ realclean.commands = $(MAKE) --directory $$sViewRoot clean
64
+ clean.depends = realclean
65
+ QMAKE_EXTRA_TARGETS += clean realclean
66
+
67
+ # Prepare make arguments
68
+ aNbJobs = $$system(getconf _NPROCESSORS_ONLN)
69
+ ST_MAKE_ARGS = -j$$aNbJobs
70
+ ST_DEBUG = 0
71
+ CONFIG(debug, debug|release) { ST_DEBUG = 1 }
72
+
73
+ #ST_MAKE_TARGET = android
74
+ !isEmpty(ST_MAKE_TARGET) { ST_MAKE_ARGS += $$ST_MAKE_TARGET }
75
+ aMakeEnvList = ST_DEBUG ANDROID_NDK ANDROID_BUILD_TOOLS ANDROID_PLATFORM ANDROID_EABI FFMPEG_ROOT FREETYPE_ROOT OPENAL_ROOT LIBCONFIG_ROOT ANDROID_KEY_GUI ANDROID_KEYSTORE ANDROID_KEYSTORE_PASSWORD ANDROID_KEY ANDROID_KEY_PASSWORD
76
+ for (aMakeEnvIter, aMakeEnvList) {
77
+ !isEmpty($${aMakeEnvIter}) { ST_MAKE_ARGS += $${aMakeEnvIter}=$$val_escape($${aMakeEnvIter}) }
78
+ }
79
+
80
+ # Redirect build to main Makefile.
81
+ QMAKE_POST_LINK += $(MAKE) --directory $$sViewRoot $$ST_MAKE_ARGS;
82
+ #realbuild.commands = $(MAKE) --directory $$sViewRoot $$ST_MAKE_ARGS
83
+ #realbuild.target = realbuild
84
+ #QMAKE_EXTRA_TARGETS += realbuild
85
+ #POST_TARGETDEPS += realbuild
86
+}
87
sview-17_04.tar.gz/docs/INSTALL.md -> sview-20_08.tar.gz/docs/INSTALL.md
Changed
16
1
2
yum install ffmpeg-devel
3
~~~~~
4
5
+ALT Linux:
6
+~~~~~
7
+apt-get install \
8
+ gcc8-c++ gcc-c++ libGLU-devel libgtk+2-devel libXrandr-devel libfreetype-devel \
9
+ libopenal-devel libconfig-devel libconfig-c++-devel libXpm-devel libwebp-devel \
10
+ libavcodec-devel libavdevice-devel libavformat-devel libavutil-devel libswscale-devel
11
+~~~~~
12
+
13
On Windows and macOS please refer to official documentation for each project.
14
Notice that DevIL and FreeImage libraries are optional and are not required for building sView
15
(libraries are loaded dynamically if available).
16
sview-17_04.tar.gz/include/StAV/StAVFrame.h -> sview-20_08.tar.gz/include/StAV/StAVFrame.h
Changed
13
1
2
return Frame->linesize[thePlaneId];
3
}
4
5
+ /**
6
+ * @return frame timestamp estimated using various heuristics, in stream time base
7
+ */
8
+ ST_CPPEXPORT int64_t getBestEffortTimestamp() const;
9
+
10
public:
11
12
AVFrame* Frame;
13
sview-20_08.tar.gz/include/StAV/StAVIOJniHttpContext.h
Added
87
1
2
+/**
3
+ * Copyright © 2019 Kirill Gavrilov <kirill@sview.ru>
4
+ *
5
+ * Distributed under the Boost Software License, Version 1.0.
6
+ * See accompanying file license-boost.txt or copy at
7
+ * http://www.boost.org/LICENSE_1_0.txt
8
+ */
9
+
10
+#ifndef __StAVIOJniHttpContext_h_
11
+#define __StAVIOJniHttpContext_h_
12
+
13
+#include <StJNI/StJNIEnv.h>
14
+#include <StAV/StAVIOContext.h>
15
+
16
+/**
17
+ * Custom AVIO context for reading http/https file using JNI
18
+ * (java.net.URLConnection and java.nio.channels.ReadableByteChannel classes).
19
+ * The main purpose of this class is providing a fallback https protocol support
20
+ * in case when FFmpeg has been built without this support.
21
+ */
22
+class StAVIOJniHttpContext : public StAVIOContext {
23
+
24
+ public:
25
+
26
+ /**
27
+ * Empty constructor.
28
+ * WARNING! av_jni_get_java_vm() will be used to attach current thread to JavaVM and initialize pointers.
29
+ * Therefore, JavaVM should be set to FFmpeg beforehand, and this context should be used only within the same working thread.
30
+ */
31
+ ST_CPPEXPORT StAVIOJniHttpContext();
32
+
33
+ /**
34
+ * Destructor. Closes open stream and detaches current thread from JavaVM.
35
+ */
36
+ ST_CPPEXPORT virtual ~StAVIOJniHttpContext();
37
+
38
+ /**
39
+ * Close the file.
40
+ */
41
+ ST_CPPEXPORT void close();
42
+
43
+ /**
44
+ * Open specified URL.
45
+ */
46
+ ST_CPPEXPORT bool open(const StString& theUrl);
47
+
48
+ /**
49
+ * Read from the file.
50
+ */
51
+ ST_CPPEXPORT virtual int read(uint8_t* theBuf,
52
+ int theBufSize) ST_ATTR_OVERRIDE;
53
+
54
+ /**
55
+ * Writing is not supported.
56
+ */
57
+ ST_LOCAL virtual int write(uint8_t* , int ) ST_ATTR_OVERRIDE { return -1; }
58
+
59
+ /**
60
+ * Seek within the file.
61
+ */
62
+ ST_CPPEXPORT virtual int64_t seek(int64_t theOffset,
63
+ int theWhence) ST_ATTR_OVERRIDE;
64
+
65
+ private:
66
+
67
+ /**
68
+ * (Re)open HTTPS stream at specific offset.
69
+ */
70
+ bool reopenReadChannel(int64_t theOffset);
71
+ struct FunctionTable;
72
+
73
+ protected:
74
+
75
+ FunctionTable* myFunctions; //!< JNI function table
76
+ StJNIEnv myJEnv; //!< JavaVM environment
77
+ StString myUrl; //!< opened URL
78
+ void* myReadChannel; //!< pointer to java.nio.channels.ReadableByteChannel
79
+ int64_t myContentLen; //!< file length
80
+ int64_t myPosition; //!< current position within the stream
81
+
82
+};
83
+
84
+ST_DEFINE_HANDLE(StAVIOJniHttpContext, StAVIOContext);
85
+
86
+#endif // __StAVIOJniHttpContext_h_
87
sview-17_04.tar.gz/include/StAV/StAVImage.h -> sview-20_08.tar.gz/include/StAV/StAVImage.h
Changed
43
1
2
/**
3
- * Copyright © 2011-2015 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2011-2020 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* Distributed under the Boost Software License, Version 1.0.
7
* See accompanying file license-boost.txt or copy at
8
9
ST_CPPEXPORT static bool resize(const StImage& theImageFrom,
10
StImage& theImageTo);
11
12
+ ST_CPPEXPORT static bool resizePlane(const StImagePlane& theImageFrom,
13
+ StImagePlane& theImageTo);
14
+
15
public:
16
17
/**
18
19
ST_CPPEXPORT virtual ~StAVImage();
20
21
/**
22
+ * Create new instance.
23
+ */
24
+ virtual StHandle<StImageFile> createEmpty() const ST_ATTR_OVERRIDE { return new StAVImage(); }
25
+
26
+ /**
27
* Close currently opened image context and release memory.
28
*/
29
- ST_CPPEXPORT virtual void close();
30
+ ST_CPPEXPORT virtual void close() ST_ATTR_OVERRIDE;
31
32
/**
33
* Decode image from specified file or memory pointer.
34
35
*/
36
ST_CPPEXPORT virtual bool save(const StString& theFilePath,
37
ImageType theImageType,
38
- StFormat theSrcFormat = StFormat_AUTO);
39
+ StFormat theSrcFormat = StFormat_AUTO) ST_ATTR_OVERRIDE;
40
41
private:
42
43
sview-17_04.tar.gz/include/StAV/StAVPacket.h -> sview-20_08.tar.gz/include/StAV/StAVPacket.h
Changed
9
1
2
DATA_PACKET,
3
FLUSH_PACKET,
4
START_PACKET,
5
+ LAST_PACKET,
6
END_PACKET,
7
QUIT_PACKET,
8
};
9
sview-17_04.tar.gz/include/StAV/stAV.h -> sview-20_08.tar.gz/include/StAV/stAV.h
Changed
140
1
2
/**
3
- * Copyright © 2011-2016 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2011-2020 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* Distributed under the Boost Software License, Version 1.0.
7
* See accompanying file license-boost.txt or copy at
8
9
#include <libavutil/spherical.h>
10
#endif
11
12
+#if(LIBAVFORMAT_VERSION_INT >= AV_VERSION_INT(57, 33, 100))
13
+ #define ST_AV_NEWCODECPAR
14
+#endif
15
+
16
+#ifndef AV_NUM_DATA_POINTERS
17
+ #define AV_NUM_DATA_POINTERS 4
18
+#endif
19
+
20
+// Compatibility with older FFmpeg (API change since 2015-07-27 - lavc 56.56.100 / 56.35.0)
21
+#ifndef AV_INPUT_BUFFER_PADDING_SIZE
22
+ #define AV_INPUT_BUFFER_PADDING_SIZE FF_INPUT_BUFFER_PADDING_SIZE
23
+#endif
24
+#ifndef AV_CODEC_FLAG_GLOBAL_HEADER
25
+ #define AV_CODEC_FLAG_GLOBAL_HEADER CODEC_FLAG_GLOBAL_HEADER
26
+#endif
27
+#ifndef AV_CODEC_FLAG2_IGNORE_CROP
28
+ #define AV_CODEC_FLAG2_IGNORE_CROP CODEC_FLAG2_IGNORE_CROP
29
+#endif
30
+
31
#ifdef _MSC_VER
32
#pragma warning(default : 4244)
33
#endif
34
35
ST_SHARED_CPPEXPORT AVPixelFormat GRAY16; //!< Y, 16bpp
36
// planar YUV formats
37
ST_SHARED_CPPEXPORT AVPixelFormat YUV420P; //!< planar YUV 4:2:0, 12bpp, (1 Cr & Cb sample per 2x2 Y samples)
38
+ ST_SHARED_CPPEXPORT AVPixelFormat YUVA420P; //!< planar YUV 4:2:0, 20bpp, (1 Cr & Cb sample per 2x2 Y & A samples)
39
ST_SHARED_CPPEXPORT AVPixelFormat YUV422P; //!< planar YUV 4:2:2, 16bpp, (1 Cr & Cb sample per 2x1 Y samples)
40
+ ST_SHARED_CPPEXPORT AVPixelFormat YUVA422P; //!< planar YUV 4:2:2 24bpp, (1 Cr & Cb sample per 2x1 Y & A samples)
41
ST_SHARED_CPPEXPORT AVPixelFormat YUV444P; //!< planar YUV 4:4:4, 24bpp, (1 Cr & Cb sample per 1x1 Y samples)
42
+ ST_SHARED_CPPEXPORT AVPixelFormat YUVA444P; //!< planar YUV 4:4:4 32bpp, (1 Cr & Cb sample per 1x1 Y & A samples)
43
ST_SHARED_CPPEXPORT AVPixelFormat YUV410P; //!< planar YUV 4:1:0, 9bpp, (1 Cr & Cb sample per 4x4 Y samples)
44
ST_SHARED_CPPEXPORT AVPixelFormat YUV411P; //!< planar YUV 4:1:1, 12bpp, (1 Cr & Cb sample per 4x1 Y samples)
45
ST_SHARED_CPPEXPORT AVPixelFormat YUV440P; //!< planar YUV 4:4:0 (1 Cr & Cb sample per 1x2 Y samples)
46
47
// XYZ formats
48
ST_SHARED_CPPEXPORT AVPixelFormat XYZ12;
49
// HWAccel formats
50
- ST_SHARED_CPPEXPORT AVPixelFormat DXVA2_VLD;
51
+ ST_SHARED_CPPEXPORT AVPixelFormat DXVA2_VLD; // Windows
52
+ ST_SHARED_CPPEXPORT AVPixelFormat VIDEOTOOLBOX_VLD; // macOS
53
54
+ /**
55
+ * @sa StImage::formatImgPixelFormat()
56
+ */
57
ST_CPPEXPORT StCString getString(const AVPixelFormat theFrmt);
58
}
59
60
61
int heightV;
62
int bitsPerComp;
63
bool isFullScale;
64
+ bool hasAlpha;
65
};
66
67
/**
68
69
}
70
71
/**
72
+ * Return codec context from the stream using deprecated API.
73
+ * The new API suggests using AVStream::codecpar, but this is confusing.
74
+ * So we would better waiting until old API is completely removed.
75
+ */
76
+ inline AVCodecContext* getCodecCtx(const AVStream* theStream) {
77
+ ST_DISABLE_DEPRECATION_WARNINGS
78
+ return theStream->codec;
79
+ ST_ENABLE_DEPRECATION_WARNINGS
80
+ }
81
+
82
+ /**
83
+ * Get codec type from the stream.
84
+ */
85
+ inline AVMediaType getCodecType(const AVStream* theStream) {
86
+ #ifdef ST_AV_NEWCODECPAR
87
+ return theStream->codecpar->codec_type;
88
+ #else
89
+ return theStream->codec->codec_type;
90
+ #endif
91
+ }
92
+
93
+ /**
94
+ * Get codec id from the stream.
95
+ */
96
+ inline AVCodecID getCodecId(const AVStream* theStream) {
97
+ #ifdef ST_AV_NEWCODECPAR
98
+ return theStream->codecpar->codec_id;
99
+ #else
100
+ return theStream->codec->codec_id;
101
+ #endif
102
+ }
103
+
104
+ /**
105
* av_version_info() wrapper; return FFmpeg version info.
106
*/
107
ST_CPPEXPORT StString getVersionInfo();
108
109
ST_CPPEXPORT bool setJavaVM(void* theJavaVM);
110
111
/**
112
+ * avio_enum_protocols() wrapper for checking input protocol.
113
+ */
114
+ ST_CPPEXPORT bool isEnabledInputProtocol(const StString& theProtocol);
115
+
116
+ /**
117
* Audio functions
118
*/
119
namespace audio {
120
121
return readTag(getFrameMetadata(theFrame), theKey, theValue);
122
}
123
124
+ /**
125
+ * Retrieve language id from the stream.
126
+ */
127
+ inline StString readLang(AVStream* theStream) {
128
+ #if(LIBAVUTIL_VERSION_INT >= AV_VERSION_INT(51, 5, 0))
129
+ StString aLang;
130
+ stAV::meta::readTag(theStream, stCString("language"), aLang);
131
+ return aLang;
132
+ #else
133
+ return theStream->language;
134
+ #endif
135
+ }
136
+
137
}
138
139
#ifdef ST_AV_NEWSTEREO
140
sview-17_04.tar.gz/include/StCore/StAndroidGlue.h -> sview-20_08.tar.gz/include/StCore/StAndroidGlue.h
Changed
143
1
2
#ifndef __StAndroidGlue_h_
3
#define __StAndroidGlue_h_
4
5
+#include "StVirtualKeys.h"
6
+
7
#include <StSlots/StSignal.h>
8
#include <StStrings/StString.h>
9
#include <StThreads/StMutex.h>
10
11
12
class StAndroidGlue;
13
class StApplication;
14
+class StKeysState;
15
16
/**
17
* Data associated with an ALooper fd that will be returned as the "outData" when that source has data ready.
18
19
};
20
21
/**
22
- * The sentry class for attaching the current thread to JavaVM.
23
- */
24
-class StJNIEnv {
25
-
26
- public:
27
-
28
- /**
29
- * Main constructor, tries to attach JavaVM to the current thread.
30
- */
31
- ST_CPPEXPORT StJNIEnv(JavaVM* theJavaVM);
32
-
33
- /**
34
- * Destructor, automatically detaches JavaVM from current thread.
35
- * Has no effect if JavaVM has been attached to the thread before creating this sentry.
36
- */
37
- ST_CPPEXPORT ~StJNIEnv();
38
-
39
- /**
40
- * Detach from current thread right now.
41
- * Has no effect if JavaVM has been attached to the thread before creating this sentry.
42
- */
43
- ST_CPPEXPORT void detach();
44
-
45
- /**
46
- * Cast to actual JNIEnv instance.
47
- */
48
- ST_LOCAL JNIEnv* operator->() const {
49
- return myJniEnv;
50
- }
51
-
52
- /**
53
- * Return true if JNI environment is NULL.
54
- */
55
- ST_LOCAL bool isNull() const { return myJniEnv == NULL; }
56
-
57
- private:
58
-
59
- JavaVM* myJavaVM; //!< pointer to global Java VM instance
60
- JNIEnv* myJniEnv; //!< JNI environment for working thread
61
- bool myToDetach; //!< flag to detach
62
-
63
-};
64
-
65
-/**
66
* Interface for the standard glue code of a threaded application.
67
*/
68
class StAndroidGlue {
69
70
ST_CPPEXPORT void setWindowFlags(const int theFlags);
71
72
/**
73
+ * Setup window title.
74
+ */
75
+ ST_CPPEXPORT void setWindowTitle(const StString& theTitle);
76
+
77
+ /**
78
+ * Set/release WAKE_LOCK.
79
+ */
80
+ ST_CPPEXPORT void setWakeLock(const StString& theTitle, bool theToLock);
81
+
82
+ /**
83
* Turn stereo output on using device-specific API.
84
*/
85
ST_CPPEXPORT void setHardwareStereoOn(const bool theToEnable);
86
87
* @param theNewFile pop onNewIntent() open file event
88
* @param theQuaternion device orientation
89
* @param theToSwapEyes swap left/right views
90
+ * @param theKeys keys state
91
*/
92
ST_CPPEXPORT void fetchState(StString& theNewFile,
93
StQuaternion<double>& theQuaternion,
94
- bool& theToSwapEyes);
95
+ bool& theToSwapEyes,
96
+ const StKeysState& theKeys);
97
98
/**
99
* Return device memory class.
100
101
* Read the open file from currently set intent.
102
* The method calls the Java method readOpenPath() of StActivity which will call setOpenPath().
103
*/
104
- ST_CPPEXPORT void readOpenPath();
105
+ ST_CPPEXPORT void readOpenPath(bool theToNullifyIntent);
106
107
ST_CPPEXPORT void printConfig();
108
ST_CPPEXPORT void freeSavedState();
109
110
*/
111
ST_LOCAL void setSwapEyes(bool theToSwapLR);
112
113
+ /**
114
+ * Return TRUE if key is processed by application.
115
+ */
116
+ ST_LOCAL bool isKeyOverridden(int theKeyCode);
117
+
118
private: //! @name ANativeActivity callbacks
119
120
ST_LOCAL static void processInputWrapper(StAndroidGlue* theApp,
121
122
AInputQueue* myInputQueuePending;
123
ANativeWindow* myWindow; //!< native window to draw into
124
ANativeWindow* myWindowPending;
125
+ StString myWindowTitle; //!< window title
126
+ StString myWakeLockTitle; //!< wake lock title
127
bool myIsChangingSurface; //!< flag indicating surface changing state
128
+ bool myIsWakeLockSet; //!< flag indicating WAKE_LOCK enabled state
129
int myWindowFlags; //!< active window flags
130
int myActivityState; //!< Current state of the app's activity (APP_CMD_START, APP_CMD_RESUME, APP_CMD_PAUSE, or APP_CMD_STOP)
131
int myMemoryClassMiB; //!< device memory class
132
133
StAndroidPollSource myInputPollSource;
134
135
StMutex myFetchLock; //!< fetch data lock
136
+ bool myRegKeys[ST_VK_NB]; //!< map of registered (used in hot-key combinations) keys
137
StString myStAppClass; //!< application class name (e.g. image, video)
138
+ StString myBuildModel; //!< android.os.Build.MODEL
139
+ StString myBuildDevice; //!< android.os.Build.DEVICE
140
StString myStereoApiId; //!< stereo API identifier
141
bool myToEnableStereoHW; //!< on/off state of stereo API
142
StString myDndPath; //!< intent data string
143
sview-17_04.tar.gz/include/StCore/StApplication.h -> sview-20_08.tar.gz/include/StCore/StApplication.h
Changed
57
1
2
/**
3
* StCore, window system independent C++ toolkit for writing OpenGL applications.
4
- * Copyright © 2009-2016 Kirill Gavrilov <kirill@sview.ru>
5
+ * Copyright © 2009-2017 Kirill Gavrilov <kirill@sview.ru>
6
*
7
* Distributed under the Boost Software License, Version 1.0.
8
* See accompanying file license-boost.txt or copy at
9
10
*/
11
ST_CPPEXPORT static StHandle<StOpenInfo> parseProcessArguments();
12
13
+ /**
14
+ * Read default drawer from setting.
15
+ */
16
+ ST_CPPEXPORT static bool readDefaultDrawer(StHandle<StOpenInfo>& theInfo);
17
+
18
+ /**
19
+ * @return TRUE if specified drawer is set as default in settings.
20
+ */
21
+ ST_CPPEXPORT bool isDefaultDrawer(const StString& theDrawer) const;
22
+
23
+ /**
24
+ * Save the drawer as default in settings.
25
+ */
26
+ ST_CPPEXPORT void setDefaultDrawer(const StString& theDrawer) const;
27
+
28
+ /**
29
+ * Create a named parameter for setting drawer as default.
30
+ */
31
+ ST_CPPEXPORT StHandle<StBoolParamNamed> createDefaultDrawerParam(const StString& theDrawer,
32
+ const StString& theTitle) const;
33
+
34
public:
35
36
/**
37
38
ST_CPPEXPORT int exec();
39
40
/**
41
+ * @return file to open in another drawer
42
+ */
43
+ const StHandle<StOpenInfo>& getOpenFileInOtherDrawer() const { return myOpenFileOtherApp; }
44
+
45
+ /**
46
* Return active renderer and main application window.
47
*/
48
ST_CPPEXPORT const StHandle<StWindow>& getMainWindow() const;
49
50
StHandle<StWindow> myWindow; //!< active renderer and main application window
51
StHandle<StWindow> mySwitchTo; //!< new renderer to switch to
52
StHandle<StOpenInfo> myOpenFileInfo; //!< file to open
53
+ StHandle<StOpenInfo> myOpenFileOtherApp; //!< file to open in another drawer
54
std::map< int, StHandle<StAction> >
55
myActions; //!< ID -> Action map
56
std::map< std::string, int >
57
sview-17_04.tar.gz/include/StCore/StEvent.h -> sview-20_08.tar.gz/include/StCore/StEvent.h
Changed
75
1
2
stEvent_TouchMove, //!< StTouchEvent, touch moved
3
stEvent_TouchCancel,//!< StTouchEvent, touch cancelled
4
stEvent_GestureCancel, //!< StGestureEvent, abort the gestures
5
+ stEvent_Gesture1Tap, //!< StGestureEvent, 1 finger single tap
6
stEvent_Gesture1DoubleTap, //!< StGestureEvent, 1 finger double tap
7
stEvent_Gesture2Move, //!< StGestureEvent, 2 fingers moving in sync
8
stEvent_Gesture2Rotate, //!< StGestureEvent, 2 fingers rotating
9
10
float DeltaY; //!< precise delta for vertical scroll
11
bool IsFromMultiTouch; //!< when true, scrolling is simulated from multi-touch gesture by system (OS X) and touches will come in parallel
12
13
+ /**
14
+ * Reset event.
15
+ */
16
+ void reset() {
17
+ Type = stEvent_Scroll;
18
+ Time = 0.0;
19
+ PointX = 0.0;
20
+ PointY = 0.0;
21
+ StepsX = 0;
22
+ StepsY = 0;
23
+ DeltaX = 0.0f;
24
+ DeltaY = 0.0f;
25
+ IsFromMultiTouch = false;
26
+ }
27
+
28
+ /**
29
+ * Initialize event.
30
+ */
31
+ void init(double theTime,
32
+ double thePointX,
33
+ double thePointY,
34
+ float theDeltaX,
35
+ float theDeltaY,
36
+ bool theIsFromMultiTouch) {
37
+ Type = stEvent_Scroll;
38
+ Time = theTime;
39
+ PointX = thePointX;
40
+ PointY = thePointY;
41
+ StepsX = 0;
42
+ StepsY = 0;
43
+ DeltaX = theDeltaX;
44
+ DeltaY = theDeltaY;
45
+ IsFromMultiTouch = theIsFromMultiTouch;
46
+ }
47
+
48
+ /**
49
+ * Compute accumulated integer steps from X scroll event.
50
+ */
51
+ int accumulateStepsX(int theInc, int theStepSize) { return accumulateSteps(StepsX, theInc, theStepSize); }
52
+
53
+ /**
54
+ * Compute accumulated integer steps from Y scroll event.
55
+ */
56
+ int accumulateStepsY(int theInc, int theStepSize) { return accumulateSteps(StepsY, theInc, theStepSize); }
57
+
58
+ /**
59
+ * Compute accumulated integer steps from scroll event.
60
+ */
61
+ static int accumulateSteps(int& theAcc, int theInc, int theStepSize) {
62
+ theAcc += theInc;
63
+ int aNbSteps = 0;
64
+ for(; theAcc <= -theStepSize; theAcc += theStepSize) {
65
+ --aNbSteps;
66
+ }
67
+ for(; theAcc >= theStepSize; theAcc -= theStepSize) {
68
+ ++aNbSteps;
69
+ }
70
+ return aNbSteps;
71
+ }
72
};
73
74
/**
75
sview-17_04.tar.gz/include/StCore/StKeysState.h -> sview-20_08.tar.gz/include/StCore/StKeysState.h
Changed
50
1
2
/**
3
* StCore, window system independent C++ toolkit for writing OpenGL applications.
4
- * Copyright © 2013 Kirill Gavrilov <kirill@sview.ru>
5
+ * Copyright © 2013-2017 Kirill Gavrilov <kirill@sview.ru>
6
*
7
* Distributed under the Boost Software License, Version 1.0.
8
* See accompanying file license-boost.txt or copy at
9
10
ST_CPPEXPORT ~StKeysState();
11
12
/**
13
+ * Reset map of registered keys.
14
+ */
15
+ ST_CPPEXPORT void resetRegisteredKeys();
16
+
17
+ /**
18
+ * Return map of registered keys.
19
+ */
20
+ ST_LOCAL const bool* getRegisteredKeys() const { return myRegKeys; }
21
+
22
+ /**
23
+ * Register key.
24
+ */
25
+ ST_CPPEXPORT void registerKey(StVirtKey theKey);
26
+
27
+ /**
28
+ * Unregister key.
29
+ */
30
+ ST_CPPEXPORT void unregisterKey(StVirtKey theKey);
31
+
32
+ /**
33
* Release all pressed keys (window lost input focus etc.).
34
*/
35
ST_CPPEXPORT void reset();
36
37
38
private:
39
40
- mutable StMutex myLock; //!< mutex for thread-safe access
41
- bool myKeys[256]; //!< virtual keys pressed state
42
- double myTimes[256]; //!< time when key was pressed or released
43
+ mutable StMutex myLock; //!< mutex for thread-safe access
44
+ double myTimes [ST_VK_NB]; //!< time when key was pressed or released
45
+ bool myKeys [ST_VK_NB]; //!< virtual keys pressed state
46
+ bool myRegKeys[ST_VK_NB]; //!< registered keys (used by some hot-keys)
47
48
};
49
50
sview-17_04.tar.gz/include/StCore/StMonitor.h -> sview-20_08.tar.gz/include/StCore/StMonitor.h
Changed
47
1
2
/**
3
* @return current vertical refresh rate
4
*/
5
- ST_LOCAL int getFreq() const {
6
- return myFreq;
7
- }
8
+ ST_LOCAL float getFreq() const { return myFreq; }
9
10
/**
11
* @param theFrequency current vertical refresh rate
12
*/
13
- ST_LOCAL void setFreq(const int theFrequency) {
14
- myFreq = theFrequency;
15
- }
16
+ ST_LOCAL void setFreq(float theFrequency) { myFreq = theFrequency; }
17
18
/**
19
* @return maximal vertical refresh rate
20
*/
21
- ST_LOCAL int getFreqMax() const {
22
- return myFreqMax;
23
- }
24
+ ST_LOCAL float getFreqMax() const { return myFreqMax; }
25
26
/**
27
* @param theFrequencyMax maximal vertical refresh rate
28
*/
29
- ST_LOCAL void setFreqMax(const int theFrequencyMax) {
30
- myFreqMax = theFrequencyMax;
31
- }
32
+ ST_LOCAL void setFreqMax(float theFrequencyMax) { myFreqMax = theFrequencyMax; }
33
34
/**
35
* @return GPU to which monitor is connected to
36
37
StEDIDParser myEdid; //!< EDID data block if available
38
StRectI_t myRect; //!< virtual space (rectangle)
39
int mySysId; //!< monitor id
40
- int myFreq; //!< frequency in Hertz
41
- int myFreqMax; //!< maximum frequency in Hertz
42
+ float myFreq; //!< frequency in Hertz
43
+ float myFreqMax; //!< maximum frequency in Hertz
44
float myScale; //!< hight pixel density scale factor
45
Orientation myOrient; //!< monitor orientation
46
47
sview-17_04.tar.gz/include/StCore/StVirtualKeys.h -> sview-20_08.tar.gz/include/StCore/StVirtualKeys.h
Changed
40
1
2
/**
3
* StCore, window system independent C++ toolkit for writing OpenGL applications.
4
- * Copyright © 2007-2015 Kirill Gavrilov <kirill@sview.ru>
5
+ * Copyright © 2007-2020 Kirill Gavrilov <kirill@sview.ru>
6
*
7
* Distributed under the Boost Software License, Version 1.0.
8
* See accompanying file license-boost.txt or copy at
9
10
ST_VK_OEM_MINUS = 0xBD, // 189 = VK_OEM_MINUS | '-' any country
11
ST_VK_PERIOD = 0xBE, // 190 = VK_OEM_PERIOD | '.' any country
12
ST_VK_SLASH = 0xBF, // 191 = VK_OEM_2 | '/?' for US
13
- ///ST_VK_OEM_3 = 0xC0, // 192 = VK_OEM_3 | '`~' for US*
14
+ ST_VK_TILDE = 0xC0, // 192 = VK_OEM_3 | '`~' for US*
15
16
ST_VK_BRACKETLEFT = 0xDB, // 219 = VK_OEM_4 | '[{' for US
17
ST_VK_BACKSLASH = 0xDC, // 220 = VK_OEM_5 | '\|' for US
18
19
ST_VK_FUNCTION = 0xD9, // 217 | OS X fn key (NSFunctionKeyMask)
20
21
};
22
+enum {
23
+ ST_VK_NB = 256 //!< maximum number of virtual keys
24
+};
25
+
26
+/**
27
+ * Remove modifiers from hot key combination and return the base virtual key.
28
+ */
29
+ST_LOCAL inline StVirtKey getBaseKeyFromHotKey(unsigned int theHotKey) {
30
+ unsigned int aKey = theHotKey & ~(ST_VF_SHIFT | ST_VF_CONTROL | ST_VF_MENU | ST_VF_COMMAND | ST_VF_FUNCTION);
31
+ if(aKey == 0
32
+ || aKey >= ST_VK_NB) {
33
+ return ST_VK_NULL;
34
+ }
35
+ return (StVirtKey )aKey;
36
+}
37
38
/**
39
* Encode single Virtual Key.
40
sview-17_04.tar.gz/include/StCore/StWindow.h -> sview-20_08.tar.gz/include/StCore/StWindow.h
Changed
70
1
2
StWinAttr_SlaveMon, //!< integer, slave window monitor id, 1 by default
3
StWinAttr_SplitCfg, //!< StWinSplit, split master window
4
StWinAttr_ToAlignEven, //!< boolean, align window position to even numbers, FALSE by default
5
+ StWinAttr_ExclusiveFullScreen, //!< boolean, exclusive fullscreen mode, FALSE by default
6
};
7
8
typedef struct tagStSlaveWindowCfg {
9
10
* @param theWinEnum subwindow ID
11
* @return rectangle within window from bottom-left corner (ready for OpenGL calls)
12
*/
13
- ST_CPPEXPORT StGLBoxPx stglViewport(const int theWinEnum) const;
14
+ ST_CPPEXPORT virtual StGLBoxPx stglViewport(const int theWinEnum) const;
15
16
/**
17
* @return GUI scale factor for compatibility with low-resolution and high-resolution displays
18
19
ST_CPPEXPORT void setStereoOutput(bool theStereoState);
20
21
/**
22
+ * Return maximum display update framerate.
23
+ */
24
+ ST_CPPEXPORT virtual float getMaximumTargetFps() const;
25
+
26
+ /**
27
* @return FPS control rule
28
*/
29
ST_CPPEXPORT double getTargetFps() const;
30
31
ST_CPPEXPORT virtual StQuaternion<double> getDeviceOrientation() const;
32
33
/**
34
+ * Return custom stereo projection frustums.
35
+ */
36
+ ST_CPPEXPORT virtual bool getCustomProjection(StRectF_t& theLeft, StRectF_t& theRight) const;
37
+
38
+ /**
39
* Return TRUE if Left/Right eyes should be swapped by external event.
40
*/
41
ST_CPPEXPORT virtual bool toSwapEyesHW() const;
42
43
ST_CPPEXPORT void stglSwap(const int theWinEnum);
44
45
/**
46
- * This method should be called only by inheritors
47
- * to override keyboard input logic.
48
- * @return cached keyboard keys state for this window
49
- */
50
- ST_CPPEXPORT StKeysState& changeKeysState();
51
-
52
- /**
53
* @return upload time in seconds
54
*/
55
ST_CPPEXPORT double getEventTime(const uint32_t theTime) const;
56
57
58
public:
59
60
+ /**
61
+ * This method should be called only by inheritors
62
+ * to override keyboard input logic.
63
+ * @return cached keyboard keys state for this window
64
+ */
65
+ ST_CPPEXPORT StKeysState& changeKeysState();
66
+
67
ST_CPPEXPORT void* getNativeOglWin() const;
68
ST_CPPEXPORT void* getNativeOglDC() const;
69
ST_CPPEXPORT void* getNativeOglRC() const;
70
sview-17_04.tar.gz/include/StFT/StFTFont.h -> sview-20_08.tar.gz/include/StFT/StFTFont.h
Changed
198
1
2
StString Italic;
3
StString BoldItalic;
4
5
- ST_LOCAL StFTFontFamily() {}
6
+ // face index within font container
7
+ int RegularFace;
8
+ int BoldFace;
9
+ int ItalicFace;
10
+ int BoldItalicFace;
11
+
12
+ ST_LOCAL StFTFontFamily() : RegularFace (0), BoldFace (0), ItalicFace (0), BoldItalicFace (0) {}
13
};
14
15
struct StFTFontPack {
16
StFTFontFamily Western;
17
StFTFontFamily CJK;
18
StFTFontFamily Korean;
19
+ StFTFontFamily Arabic; //!< fallback font for Arabic letters
20
+ StFTFontFamily MiscSymbols; //!< fallback font for Miscellaneous Symbols
21
};
22
23
/**
24
25
*/
26
enum Subset {
27
Subset_General,
28
- Subset_Korean, //!< modern Korean letters
29
- Subset_CJK, //!< Chinese characters (Chinese, Japanese, Korean and Vietnam)
30
+ Subset_Korean, //!< modern Korean letters
31
+ Subset_CJK, //!< Chinese characters (Chinese, Japanese, Korean and Vietnam)
32
+ Subset_Arabic, //!< Arabic characters
33
+ Subset_MiscSymbols, //!< Miscellaneous Symbols 0x2600 - 0x26FF
34
SubsetsNB
35
};
36
37
38
|| (theUChar >= 0x04E00 && theUChar <= 0x09FFF)
39
|| (theUChar >= 0x0F900 && theUChar <= 0x0FAFF)
40
|| (theUChar >= 0x20000 && theUChar <= 0x2A6DF)
41
- || (theUChar >= 0x2F800 && theUChar <= 0x2FA1F);
42
+ || (theUChar >= 0x2F800 && theUChar <= 0x2FA1F)
43
+ //
44
+ || (theUChar >= 0x030A0 && theUChar <= 0x030FF); // Katakana (Japanese) is NOT part of CJK, but CJK fonts usually include these symbols
45
}
46
47
/**
48
49
}
50
51
/**
52
+ * @return true if specified character is within subset of Miscellaneous Symbols
53
+ */
54
+ ST_LOCAL static bool isMiscSymbol(stUtf32_t theUChar) {
55
+ return (theUChar >= 0x02600 && theUChar <= 0x026FF);
56
+ }
57
+
58
+ /**
59
+ * @return true if specified character is within subset of Arabic characters
60
+ */
61
+ ST_LOCAL static bool isArabic(stUtf32_t theUChar) {
62
+ return (theUChar >= 0x00600 && theUChar <= 0x006FF);
63
+ }
64
+
65
+ /**
66
+ * @return true if specified character should be displayed in Right-to-Left order.
67
+ */
68
+ ST_LOCAL static bool isRightToLeft(stUtf32_t theUChar) {
69
+ return (theUChar >= 0x00600 && theUChar <= 0x006FF); // Arabic
70
+ }
71
+
72
+ /**
73
* Determine Unicode subset for specified character
74
*/
75
ST_LOCAL static Subset subset(const stUtf32_t theUChar) {
76
77
return Subset_CJK;
78
} else if(isKorean(theUChar)) {
79
return Subset_Korean;
80
+ } else if(isArabic(theUChar)) {
81
+ return Subset_Arabic;
82
+ } else if(isMiscSymbol(theUChar)) {
83
+ return Subset_MiscSymbols;
84
}
85
return Subset_General;
86
}
87
88
/**
89
* Load the font from specified path.
90
* @param theFontPath path to the font
91
+ * @param theFaceId face id within the file (0 by default)
92
* @param theStyle the font style
93
+ * @param theToSyntItalic synthesize italic style
94
* @return true on success
95
*/
96
- ST_CPPEXPORT bool load(const StString& theFontPath,
97
- const StFTFont::Style theStyle);
98
+ ST_CPPEXPORT bool load(const StString& theFontPath,
99
+ const int theFaceId,
100
+ const StFTFont::Style theStyle,
101
+ const bool theToSyntItalic = false);
102
103
/**
104
* Load the font from data array.
105
106
* Assuming text rendered horizontally.
107
*/
108
ST_CPPEXPORT void addAdvanceX(const stUtf32_t theUCharNext,
109
- StVec2<GLfloat>& thePen);
110
+ StVec2<GLfloat>& thePen) const;
111
112
/**
113
* Compute advance to the next character with kerning applied when applicable
114
115
* Assuming text rendered vertically.
116
*/
117
ST_CPPEXPORT void addAdvanceY(const stUtf32_t theUCharNext,
118
- StVec2<GLfloat>& thePen);
119
+ StVec2<GLfloat>& thePen) const;
120
121
/**
122
* Compute advance to the next character with kerning applied when applicable
123
124
* Compute advance to the next character with kerning applied when applicable.
125
* Assuming text rendered horizontally.
126
*/
127
- ST_CPPEXPORT float getAdvanceX(const stUtf32_t theUCharNext);
128
+ ST_CPPEXPORT float getAdvanceX(const stUtf32_t theUCharNext) const;
129
130
/**
131
* Compute advance to the next character with kerning applied when applicable.
132
133
* Compute advance to the next character with kerning applied when applicable.
134
* Assuming text rendered vertically.
135
*/
136
- ST_CPPEXPORT float getAdvanceY(const stUtf32_t theUCharNext);
137
+ ST_CPPEXPORT float getAdvanceY(const stUtf32_t theUCharNext) const;
138
139
/**
140
* Compute advance to the next character with kerning applied when applicable.
141
142
}
143
144
/**
145
+ * @return font face index
146
+ */
147
+ ST_LOCAL int getFaceIndex(const StFTFont::Style theStyle) const {
148
+ return myFontFaces[theStyle];
149
+ }
150
+
151
+ /**
152
* @return active font style
153
*/
154
ST_LOCAL StFTFont::Style getActiveStyle() const {
155
156
return mySubsets[Subset_Korean];
157
}
158
159
+ /**
160
+ * @return true if this font contains glyphs of specified subset
161
+ */
162
+ ST_LOCAL bool hasSubset(Subset theSubset) const {
163
+ return mySubsets[theSubset];
164
+ }
165
+
166
protected:
167
168
/**
169
170
*/
171
ST_CPPEXPORT bool loadGlyph(const stUtf32_t theUChar);
172
173
+ /**
174
+ * Wrapper for FT_Get_Kerning - retrieve kerning values.
175
+ */
176
+ ST_CPPEXPORT bool getKerning(FT_Vector& theKern,
177
+ const stUtf32_t theUCharCurr,
178
+ const stUtf32_t theUCharNext) const;
179
+
180
private:
181
182
/**
183
184
StFTFont::Style myStyle; //!< active FT face style
185
FT_Face myFTFaces[StylesNB]; //!< FT face objects
186
StString myFontPaths[StylesNB]; //!< font paths
187
+ int myFontFaces[StylesNB]; //!< font face ids
188
bool mySubsets[SubsetsNB];
189
FT_Int32 myLoadFlags; //!< default load flags
190
unsigned int myGlyphMaxWidth; //!< maximum glyph width
191
unsigned int myGlyphMaxHeight; //!< maximum glyph height
192
193
StImagePlane myGlyphImg; //!< cached glyph plane
194
- FT_Vector myKernAdvance; //!< buffer variable
195
stUtf32_t myUChar; //!< currently loaded unicode character
196
197
};
198
sview-17_04.tar.gz/include/StFT/StFTFontRegistry.h -> sview-20_08.tar.gz/include/StFT/StFTFontRegistry.h
Changed
13
1
2
void searchFiles(const StArrayList<StString>& theNames,
3
const bool theIsMajor);
4
5
+ /**
6
+ * Process font file.
7
+ */
8
+ bool registerFamily(const StString& theFontPath, int theFaceId);
9
+
10
private:
11
12
StArrayList<StString> myExtensions; //!< list of supported font file extensions
13
sview-17_04.tar.gz/include/StFile/StFileNode.h -> sview-20_08.tar.gz/include/StFile/StFileNode.h
Changed
76
1
2
/**
3
- * Copyright © 2010-2013 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2010-2017 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* Distributed under the Boost Software License, Version 1.0.
7
* See accompanying file license-boost.txt or copy at
8
9
#define __StFileNode_H__
10
11
#include <StFile/StNode.h>
12
-#include <StFile/StMIME.h>
13
+#include <StFile/StMIMEList.h>
14
#include <StTemplates/StHandle.h>
15
16
-class StMIMEList;
17
+/**
18
+ * Structure defining Open File dialog content.
19
+ */
20
+struct StOpenFileName {
21
+ StString Folder; //!< folder to open
22
+ StString Title; //!< dialog title
23
+ StMIMEList Filter; //!< main file filter
24
+ StString FilterTitle; //!< main file filter title; "All supported" will be displayed when empty
25
+ StMIMEList ExtraFilter; //!< extra file filter (optional)
26
+ StString ExtraFilterTitle; //!< extra file filter title
27
+};
28
+
29
class StFileNode : public StNode {
30
31
private:
32
33
ST_CPPEXPORT static bool isFileExists(const StCString& thePath);
34
35
/**
36
+ * @param thePath file path
37
+ * @return true if file/folder has read-only flag
38
+ */
39
+ ST_CPPEXPORT static bool isFileReadOnly(const StCString& thePath);
40
+
41
+ /**
42
+ * @param thePath file path
43
+ * @return true if file attributes have been successfully modified
44
+ */
45
+ ST_CPPEXPORT static bool removeReadOnlyFlag(const StCString& thePath);
46
+
47
+ /**
48
* Tries to remove file from filesystem.
49
* @return true on success.
50
*/
51
52
53
/**
54
* Open native system open file dialog.
55
- * @param theFolder path to open
56
- * @param theTitle dialog title
57
- * @param theFilter files filter
58
- * @param theOutFilePath file selected by user
59
- * @param toSave flag this dialog to open or save file
60
+ * @param theFilePath [in] [out] file selected by user
61
+ * @param theInfo [in] file open dialog definition
62
+ * @param theToSave [in] flag this dialog to open or save file
63
* @return
64
*/
65
- ST_CPPEXPORT static bool openFileDialog(const StString& theFolder,
66
- const StString& theTitle,
67
- const StMIMEList& theFilter,
68
- StString& theOutFilePath,
69
- bool toSave);
70
+ ST_CPPEXPORT static bool openFileDialog(StString& theFilePath,
71
+ const StOpenFileName& theInfo,
72
+ bool theToSave);
73
74
/**
75
* Function used where not possible use native Unicode paths.
76
sview-17_04.tar.gz/include/StFile/StFolder.h -> sview-20_08.tar.gz/include/StFile/StFolder.h
Changed
8
1
2
/**
3
- * Copyright © 2009-2014 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2009-2017 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* Distributed under the Boost Software License, Version 1.0.
7
* See accompanying file license-boost.txt or copy at
8
sview-17_04.tar.gz/include/StFile/StMIMEList.h -> sview-20_08.tar.gz/include/StFile/StMIMEList.h
Changed
21
1
2
}
3
4
/**
5
+ * Verify the filename extension is in supported list.
6
+ */
7
+ bool checkExtension(const StString& theExt) const {
8
+ for(size_t aMimeId = 0; aMimeId < StArrayList<StMIME>::size(); ++aMimeId) {
9
+ const StString& anExt = StArrayList<StMIME>::getValue(aMimeId).getExtension();
10
+ if(anExt.isEqualsIgnoreCase(theExt)) {
11
+ return true;
12
+ }
13
+ }
14
+ return false;
15
+ }
16
+
17
+ /**
18
* Returns toString, splitter argument should not be changed!
19
* @param theSplitter (const StString& ) - splitter char should not be changed!
20
* @return string (StString ).
21
sview-17_04.tar.gz/include/StFile/StNode.h -> sview-20_08.tar.gz/include/StFile/StNode.h
Changed
28
1
2
}
3
4
virtual StString getPath() const {
5
- if(getParent() != NULL) {
6
- StString parentPath = getParent()->getPath();
7
- if(parentPath.isEmpty()) {
8
- return subPath;
9
- } else {
10
- return parentPath + StString(SYS_FS_SPLITTER) + subPath;
11
- }
12
+ if(getParent() == NULL) {
13
+ return subPath;
14
}
15
- return subPath;
16
+
17
+ const StString parentPath = getParent()->getPath();
18
+ if(parentPath.isEmpty()) {
19
+ return subPath;
20
+ }
21
+
22
+ return parentPath.isEndsWith(SYS_FS_SPLITTER)
23
+ ? parentPath + subPath
24
+ : parentPath + StString(SYS_FS_SPLITTER) + subPath;
25
}
26
27
bool operator==(const StNode& compare) const {
28
sview-17_04.tar.gz/include/StFile/StRawFile.h -> sview-20_08.tar.gz/include/StFile/StRawFile.h
Changed
23
1
2
ST_CPPEXPORT void initBuffer(size_t theDataSize);
3
4
/**
5
+ * Wrap external buffer.
6
+ */
7
+ ST_CPPEXPORT void wrapBuffer(stUByte_t* theBuffer,
8
+ size_t theDataSize);
9
+
10
+
11
+ /**
12
* Free current buffer.
13
*/
14
ST_CPPEXPORT void freeBuffer();
15
16
stUByte_t* myBuffer; //!< buffer with file content
17
size_t myBuffSize; //!< buffer size
18
size_t myLength; //!< data length
19
+ bool myIsOwnData; //!< flag indicating that myBuffer was allocated by this class
20
21
};
22
23
sview-17_04.tar.gz/include/StGL/StGLContext.h -> sview-20_08.tar.gz/include/StGL/StGLContext.h
Changed
87
1
2
/**
3
- * Copyright © 2012-2016 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2012-2019 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* Distributed under the Boost Software License, Version 1.0.
7
* See accompanying file license-boost.txt or copy at
8
9
StGLArbFbo* arbFbo; //!< GL_ARB_framebuffer_object
10
bool arbNPTW; //!< GL_ARB_texture_non_power_of_two
11
bool arbTexRG; //!< GL_ARB_texture_rg
12
+ bool arbTexFloat;//!< GL_ARB_texture_float (on desktop OpenGL - since 3.0 or as extension GL_ARB_texture_float; on OpenGL ES - since 3.0)
13
bool arbTexClear;//!< GL_ARB_clear_texture
14
- bool hasUnpack; //!< GL_PACK_ROW_LENGTH / GL_UNPACK_ROW_LENGTH can be used - OpenGL ES 3.0+ or any desktop
15
bool hasHighp; //!< highp in GLSL ES fragment shader is supported
16
bool hasTexRGBA8;//!< always available on desktop; on OpenGL ES - since 3.0 or as extension GL_OES_rgb8_rgba8
17
bool extTexBGRA8;//!< GL_EXT_texture_format_BGRA8888 for OpenGL ES
18
+ bool extTexR16; //!< GL_EXT_texture_norm16 on OpenGL ES
19
StGLFunctions* extAll; //!< access to ALL extensions for advanced users
20
bool extSwapTear;//!< WGL_EXT_swap_control_tear/GLX_EXT_swap_control_tear
21
+ bool khrFlushControl; //!< GL_KHR_context_flush_control / WGL_ARB_context_flush_control / GLX_ARB_context_flush_control / EGL_KHR_context_flush_control
22
23
public: //! @name class interface
24
25
26
/**
27
* Return capabilities of currently active device.
28
*/
29
- ST_LOCAL StGLDeviceCaps getDeviceCaps() const {
30
- StGLDeviceCaps aCaps;
31
- aCaps.maxTexDim = myMaxTexDim;
32
- aCaps.hasUnpack = hasUnpack;
33
- return aCaps;
34
- }
35
+ ST_LOCAL const StGLDeviceCaps& getDeviceCaps() const { return myDevCaps; }
36
37
ST_LOCAL GLint getVersionMajor() const {
38
return myVerMajor;
39
40
* @return value for GL_MAX_TEXTURE_SIZE.
41
*/
42
ST_LOCAL GLint getMaxTextureSize() const {
43
- return myMaxTexDim;
44
+ return myDevCaps.maxTexDim;
45
}
46
47
/**
48
49
int theLength,
50
const char* theMessage);
51
52
+ public:
53
+
54
+ /**
55
+ * Return auxiliary temporary image buffer.
56
+ */
57
+ ST_LOCAL StImagePlane& getTmpImagePlane1() { return myTmpPlane1; }
58
+
59
+ /**
60
+ * Return auxiliary temporary image buffer.
61
+ */
62
+ ST_LOCAL StImagePlane& getTmpImagePlane2() { return myTmpPlane2; }
63
+
64
public: //! @name auxiliary methods
65
66
/**
67
68
StHandle<StResourceManager>
69
myResMgr; //!< file resources manager
70
StHandle<StMsgQueue> myMsgQueue; //!< messages queue
71
+ StGLDeviceCaps myDevCaps; //!< device caps
72
GlVendor myGlVendor; //!< driver vendor
73
GPU_Name myGpuName; //!< GPU name
74
GLint myVerMajor; //!< cached GL version major number
75
GLint myVerMinor; //!< cached GL version minor number
76
- GLint myMaxTexDim; //!< maximum texture dimension
77
BufferBits myWindowBits; //!< default buffer (window) bits
78
BufferBits myFBOBits; //!< FBO bits
79
bool myWasInit; //!< initialization state
80
81
+ StImagePlane myTmpPlane1; //!< auxiliary temporary image buffer
82
+ StImagePlane myTmpPlane2; //!< auxiliary temporary image buffer
83
+
84
protected: //! @name current state
85
86
std::stack<StGLBoxPx> myScissorStack; //!< cached stack of scissor rectangles
87
sview-17_04.tar.gz/include/StGL/StGLDeviceCaps.h -> sview-20_08.tar.gz/include/StGL/StGLDeviceCaps.h
Changed
51
1
2
/**
3
- * Copyright © 2016 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2016-2019 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* Distributed under the Boost Software License, Version 1.0.
7
* See accompanying file license-boost.txt or copy at
8
9
#ifndef __StGLDeviceCaps_h_
10
#define __StGLDeviceCaps_h_
11
12
-#include <stTypes.h>
13
+#include <StImage/StImagePlane.h>
14
15
/**
16
* Structure defining OpenGL device capabilities
17
18
19
/**
20
* Device support data transferring with row unpack size specified.
21
+ * GL_PACK_ROW_LENGTH / GL_UNPACK_ROW_LENGTH can be used - OpenGL ES 3.0+ or any desktop.
22
*/
23
bool hasUnpack;
24
25
/**
26
+ * Return TRUE if image format can be uploaded into OpenGL texture.
27
+ */
28
+ bool isSupportedFormat(StImagePlane::ImgFormat theFormat) const { return mySupportedFormats[theFormat]; }
29
+
30
+ /**
31
+ * Set if image format can be uploaded into OpenGL texture.
32
+ */
33
+ void setSupportedFormat(StImagePlane::ImgFormat theFormat, bool theIsSupported) { mySupportedFormats[theFormat] = theIsSupported; }
34
+
35
+ /**
36
* Empty constructor.
37
*/
38
- ST_LOCAL StGLDeviceCaps() : maxTexDim(0), hasUnpack(true) {}
39
+ ST_LOCAL StGLDeviceCaps()
40
+ : maxTexDim(0), hasUnpack(true) {
41
+ stMemZero(mySupportedFormats, sizeof(mySupportedFormats));
42
+ }
43
+
44
+ private:
45
+
46
+ bool mySupportedFormats[StImagePlane::ImgNB];
47
+
48
};
49
50
#endif // __StGLDeviceCaps_h_
51
sview-17_04.tar.gz/include/StGL/StGLFontEntry.h -> sview-20_08.tar.gz/include/StGL/StGLFontEntry.h
Changed
16
1
2
}
3
4
/**
5
+ * @return true if this font contains glyphs of specified subset
6
+ */
7
+ ST_LOCAL bool hasSubset(StFTFont::Subset theSubset) const {
8
+ return !myFont.isNull()
9
+ && myFont->hasSubset(theSubset);
10
+ }
11
+
12
+ /**
13
* Compute glyph rectangle at specified pen position (on baseline)
14
* and render it to texture if not already.
15
* @param theCtx active context
16
sview-17_04.tar.gz/include/StGL/StGLFunctions.h -> sview-20_08.tar.gz/include/StGL/StGLFunctions.h
Changed
37
1
2
3
// include main OpenGL header provided with system
4
#if defined(__APPLE__)
5
+ #define GL_SILENCE_DEPRECATION
6
#include <OpenGL/gl.h>
7
#elif defined(ST_HAVE_GLES2) || defined(__ANDROID__)
8
#include <GLES2/gl2.h>
9
10
const int* theAttribs);
11
wglCreateContextAttribsARB_t wglCreateContextAttribsARB;
12
13
+ // WGL_ARB_context_flush_control
14
+
15
+ #define WGL_CONTEXT_RELEASE_BEHAVIOR_ARB 0x2097
16
+ #define WGL_CONTEXT_RELEASE_BEHAVIOR_NONE_ARB 0x0000
17
+ #define WGL_CONTEXT_RELEASE_BEHAVIOR_FLUSH_ARB 0x2098
18
+
19
// WGL_NV_DX_interop
20
21
typedef BOOL (WINAPI *wglDXSetResourceShareHandleNV_t)(void* theObjectD3d, HANDLE theShareHandle);
22
23
typedef int (*glXSwapIntervalSGI_t)(int theInterval);
24
glXSwapIntervalSGI_t glXSwapIntervalSGI;
25
26
+ public: //! @name GLX_ARB_context_flush_control
27
+
28
+#ifndef GLX_CONTEXT_RELEASE_BEHAVIOR_ARB
29
+ #define GLX_CONTEXT_RELEASE_BEHAVIOR_ARB 0x2097
30
+ #define GLX_CONTEXT_RELEASE_BEHAVIOR_NONE_ARB 0x0000
31
+ #define GLX_CONTEXT_RELEASE_BEHAVIOR_FLUSH_ARB 0x2098
32
+#endif
33
+
34
// GLX_MESA_query_renderer
35
36
#ifndef GLX_RENDERER_VENDOR_ID_MESA
37
sview-17_04.tar.gz/include/StGL/StGLProgram.h -> sview-20_08.tar.gz/include/StGL/StGLProgram.h
Changed
9
1
2
TEXTURE_SAMPLE_0 = 0, // GL_TEXTURE0
3
TEXTURE_SAMPLE_1 = 1, // GL_TEXTURE1
4
TEXTURE_SAMPLE_2 = 2, // GL_TEXTURE2
5
+ TEXTURE_SAMPLE_3 = 3, // GL_TEXTURE3
6
};
7
8
public:
9
sview-17_04.tar.gz/include/StGL/StGLTextFormatter.h -> sview-20_08.tar.gz/include/StGL/StGLTextFormatter.h
Changed
13
1
2
*/
3
ST_CPPEXPORT void newLine(const size_t theLastRect);
4
5
+ /**
6
+ * Flip left to right order.
7
+ */
8
+ ST_CPPEXPORT void flipLeftRight(size_t theCharFrom, size_t theCharTo);
9
+
10
protected: //! @name configuration
11
12
StAlignX myAlignX; //!< horizontal alignment style
13
sview-17_04.tar.gz/include/StGL/StGLTexture.h -> sview-20_08.tar.gz/include/StGL/StGLTexture.h
Changed
85
1
2
/**
3
- * Copyright © 2009-2015 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2009-2019 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* Distributed under the Boost Software License, Version 1.0.
7
* See accompanying file license-boost.txt or copy at
8
9
10
#include <StGL/StGLResource.h>
11
#include <StStrings/StString.h>
12
+#include <StImage/StImagePlane.h>
13
14
-class StImagePlane;
15
class StGLContext;
16
17
#define GL_TEXTURE0 0x84C0
18
19
* Currently GL_ALPHA is returned for grayscale image data.
20
* @return true if internal format was found.
21
*/
22
- ST_CPPEXPORT static bool getInternalFormat(const StGLContext& theCtx,
23
- const StImagePlane& theData,
24
- GLint& theInternalFormat);
25
+ ST_CPPEXPORT static bool getInternalFormat(const StGLContext& theCtx,
26
+ const StImagePlane::ImgFormat theFormat,
27
+ GLint& theInternalFormat);
28
29
/**
30
* Return true for GL_ALPHA / GL_RED formats.
31
32
* After this call current texture will be undefined.
33
*/
34
ST_CPPEXPORT void setMinMagFilter(StGLContext& theCtx,
35
- const GLenum theMinMagFilter);
36
+ const GLenum theMinFilter,
37
+ const GLenum theMagFilter);
38
+
39
+ /**
40
+ * Change Min and Mag filter.
41
+ * After this call current texture will be undefined.
42
+ */
43
+ ST_LOCAL void setMinMagFilter(StGLContext& theCtx,
44
+ const GLenum theMinMagFilter) {
45
+ setMinMagFilter(theCtx, theMinMagFilter, theMinMagFilter);
46
+ }
47
48
ST_LOCAL bool fill(StGLContext& theCtx,
49
const StImagePlane& theData) {
50
51
const GLenum theTarget,
52
const GLsizei theRowFrom,
53
const GLsizei theRowTo,
54
- const GLsizei theBatchRows = 128);
55
+ const GLsizei theBatchRows);
56
+
57
+ /**
58
+ * Fill the texture with the image plane.
59
+ * @param theCtx current context
60
+ * @param theData the image plane to copy data from
61
+ * @param theTarget texture target
62
+ * @param theRowFrom fill data from row (for both - input image plane and the texture!)
63
+ * @param theRowTo fill data up to the row (0 means all rows)
64
+ * @return true on success
65
+ */
66
+ ST_CPPEXPORT bool fillPatch(StGLContext& theCtx,
67
+ const StImagePlane& theData,
68
+ const GLenum theTarget,
69
+ const GLsizei theRowFrom,
70
+ const GLsizei theRowTo);
71
72
/**
73
* @return GL texture ID.
74
75
GLint myTextFormat; //!< texture format - GL_RGB, GL_RGBA,...
76
GLuint myTextureId; //!< GL texture ID
77
GLenum myTextureUnit; //!< texture unit
78
- GLenum myTextureFilt; //!< current texture filter
79
+ GLenum myFilterMin; //!< current minify texture filter (GL_TEXTURE_MIN_FILTER)
80
+ GLenum myFilterMag; //!< current magnify texture filter (GL_TEXTURE_MAG_FILTER)
81
+ int myHasMipMaps; //!< indicates if mip levels have been generated
82
83
private:
84
85
sview-17_04.tar.gz/include/StGL/StParams.h -> sview-20_08.tar.gz/include/StGL/StParams.h
Changed
135
1
2
/**
3
- * Copyright © 2009-2017 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2009-2020 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* Distributed under the Boost Software License, Version 1.0.
7
* See accompanying file license-boost.txt or copy at
8
9
* Surface to map image onto.
10
*/
11
enum StViewSurface {
12
- StViewSurface_Plain, //!< normal 2D image
13
- StViewSurface_Cubemap, //!< cubemap texture
14
- StViewSurface_Sphere, //!< spherical panorama
15
- //StViewSurface_Cylinder, //!< cylindrical panorama
16
+ StViewSurface_Plain, //!< normal 2D image
17
+ StViewSurface_Theater, //!< theater panorama
18
+ StViewSurface_Cubemap, //!< cubemap texture
19
+ StViewSurface_Sphere, //!< spherical panorama, 360 degrees
20
+ StViewSurface_Hemisphere, //!< spherical panorama, 180 degrees
21
+ StViewSurface_Cylinder, //!< cylindrical panorama
22
+ StViewSurface_CubemapEAC, //!< equi-angular cubemap
23
};
24
25
/**
26
27
28
static StString GET_VIEW_MODE_NAME(StViewSurface theViewMode) {
29
switch(theViewMode) {
30
- case StViewSurface_Cubemap: return "cubemap";
31
- case StViewSurface_Sphere: return "sphere";
32
- case StViewSurface_Plain: return "flat";
33
+ case StViewSurface_Cubemap: return "cubemap";
34
+ case StViewSurface_CubemapEAC: return "eac";
35
+ case StViewSurface_Sphere: return "sphere";
36
+ case StViewSurface_Hemisphere: return "hemisphere";
37
+ case StViewSurface_Cylinder: return "cylinder";
38
+ case StViewSurface_Theater: return "theater";
39
+ case StViewSurface_Plain: return "flat";
40
}
41
return "flat";
42
}
43
44
static StViewSurface GET_VIEW_MODE_FROM_STRING(const StString& theViewModeStr) {
45
if(theViewModeStr.isStartsWithIgnoreCase(stCString("cubemap"))) {
46
return StViewSurface_Cubemap;
47
+ } else if(theViewModeStr.isStartsWithIgnoreCase(stCString("eac"))) {
48
+ return StViewSurface_CubemapEAC;
49
} else if(theViewModeStr.isStartsWithIgnoreCase(stCString("sphere"))) {
50
return StViewSurface_Sphere;
51
+ } else if(theViewModeStr.isStartsWithIgnoreCase(stCString("hemisphere"))) {
52
+ return StViewSurface_Hemisphere;
53
+ } else if(theViewModeStr.isStartsWithIgnoreCase(stCString("cylinder"))) {
54
+ return StViewSurface_Cylinder;
55
+ } else if(theViewModeStr.isStartsWithIgnoreCase(stCString("theater"))) {
56
+ return StViewSurface_Theater;
57
} else {
58
return StViewSurface_Plain;
59
}
60
}
61
62
+ /**
63
+ * Convert panorama mode into surface view.
64
+ */
65
+ static StViewSurface getViewSurfaceForPanoramaSource(StPanorama thePano, bool theToFallbackSphere) {
66
+ switch(thePano) {
67
+ case StPanorama_Cubemap6_1:
68
+ case StPanorama_Cubemap1_6:
69
+ case StPanorama_Cubemap3_2:
70
+ return StViewSurface_Cubemap;
71
+ case StPanorama_Cubemap3_2ytb:
72
+ case StPanorama_Cubemap2_3ytb:
73
+ return StViewSurface_CubemapEAC;
74
+ case StPanorama_Sphere:
75
+ return StViewSurface_Sphere;
76
+ case StPanorama_Hemisphere:
77
+ return StViewSurface_Hemisphere;
78
+ case StPanorama_OFF:
79
+ break;
80
+ }
81
+ return theToFallbackSphere ? StViewSurface_Sphere : StViewSurface_Plain;
82
+ }
83
+
84
public:
85
86
/**
87
88
void moveToRight(const float theDuration = 0.02f) {
89
switch(ViewingMode) {
90
case StViewSurface_Sphere:
91
+ case StViewSurface_Hemisphere:
92
+ case StViewSurface_Cylinder:
93
+ case StViewSurface_Theater:
94
case StViewSurface_Cubemap:
95
+ case StViewSurface_CubemapEAC:
96
myPanYaw += 100.0f * theDuration;
97
break;
98
case StViewSurface_Plain:
99
100
void moveToLeft(const float theDuration = 0.02f) {
101
switch(ViewingMode) {
102
case StViewSurface_Sphere:
103
+ case StViewSurface_Hemisphere:
104
+ case StViewSurface_Cylinder:
105
+ case StViewSurface_Theater:
106
case StViewSurface_Cubemap:
107
+ case StViewSurface_CubemapEAC:
108
myPanYaw -= 100.0f * theDuration;
109
break;
110
case StViewSurface_Plain:
111
112
void moveToDown(const float theDuration = 0.02f) {
113
switch(ViewingMode) {
114
case StViewSurface_Sphere:
115
+ case StViewSurface_Hemisphere:
116
+ case StViewSurface_Cylinder:
117
+ case StViewSurface_Theater:
118
case StViewSurface_Cubemap:
119
+ case StViewSurface_CubemapEAC:
120
myPanPitch = clipPitch(myPanPitch - 100.0f * theDuration);
121
break;
122
case StViewSurface_Plain:
123
124
void moveToUp(const float theDuration = 0.02f) {
125
switch(ViewingMode) {
126
case StViewSurface_Sphere:
127
+ case StViewSurface_Hemisphere:
128
+ case StViewSurface_Cylinder:
129
+ case StViewSurface_Theater:
130
case StViewSurface_Cubemap:
131
+ case StViewSurface_CubemapEAC:
132
myPanPitch = clipPitch(myPanPitch + 100.0f * theDuration);
133
break;
134
case StViewSurface_Plain:
135
sview-17_04.tar.gz/include/StGLMesh/StGLMesh.h -> sview-20_08.tar.gz/include/StGLMesh/StGLMesh.h
Changed
10
1
2
return myNormals;
3
}
4
5
+ ST_LOCAL StArrayList<StGLVec4>& changeColors() { return myColors; }
6
+
7
inline StArrayList<GLuint>& changeIndices() {
8
return myIndices;
9
}
10
sview-20_08.tar.gz/include/StGLMesh/StGLUVCylinder.h
Added
71
1
2
+/**
3
+ * Copyright © 2019-2020 Kirill Gavrilov <kirill@sview.ru>
4
+ *
5
+ * Distributed under the Boost Software License, Version 1.0.
6
+ * See accompanying file license-boost.txt or copy at
7
+ * http://www.boost.org/LICENSE_1_0.txt
8
+ */
9
+
10
+#ifndef __StGLUVCylinder_h_
11
+#define __StGLUVCylinder_h_
12
+
13
+#include "StGLMesh.h"
14
+
15
+class StBndSphere;
16
+
17
+/**
18
+ * Class represents configurable UV cylinder with computed vertices, normales, texture coordinates.
19
+ */
20
+class StGLUVCylinder : public StGLMesh {
21
+
22
+ public:
23
+
24
+ /**
25
+ * Defines the UV cylinder mesh with specified parameters.
26
+ */
27
+ ST_CPPEXPORT StGLUVCylinder(const StGLVec3& theCenter,
28
+ const float theHeight,
29
+ const float theRadius,
30
+ const int theRings);
31
+
32
+ /**
33
+ * Defines the UV cylinder mesh with specified parameters.
34
+ */
35
+ ST_CPPEXPORT StGLUVCylinder(const StGLVec3& theCenter,
36
+ const float theHeight,
37
+ const float theRadius,
38
+ const float theAngleFrom,
39
+ const float theAngleTo,
40
+ const int theRings);
41
+
42
+ ST_CPPEXPORT virtual ~StGLUVCylinder();
43
+
44
+ /**
45
+ * Compute the mesh using current configuration.
46
+ */
47
+ ST_CPPEXPORT virtual bool computeMesh() ST_ATTR_OVERRIDE;
48
+
49
+ ST_LOCAL float getRadius() const { return myRadius; }
50
+ ST_LOCAL void setRadius(float theRadius) { myRadius = theRadius; }
51
+ ST_LOCAL float getHeight() const { return myHeight; }
52
+ ST_LOCAL void setHeight(float theHeight) { myHeight = theHeight; }
53
+ ST_LOCAL float getAngleFrom() const { return myAngleFrom; }
54
+ ST_LOCAL void setAngleFrom(float theAngle) { myAngleFrom = theAngle; }
55
+ ST_LOCAL float getAngleTo() const { return myAngleTo; }
56
+ ST_LOCAL void setAngleTo(float theAngle) { myAngleTo = theAngle; }
57
+ ST_LOCAL float getAngle() const { return myAngleTo - myAngleFrom; }
58
+
59
+ private:
60
+
61
+ StGLVec3 myCenter;
62
+ float myRadius;
63
+ float myHeight;
64
+ float myAngleFrom;
65
+ float myAngleTo;
66
+ int myNbRings;
67
+
68
+};
69
+
70
+#endif //__StGLUVCylinder_h_
71
sview-17_04.tar.gz/include/StGLMesh/StGLUVSphere.h -> sview-20_08.tar.gz/include/StGLMesh/StGLUVSphere.h
Changed
26
1
2
/**
3
- * Copyright © 2010-2013 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2010-2019 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* Distributed under the Boost Software License, Version 1.0.
7
* See accompanying file license-boost.txt or copy at
8
9
*/
10
ST_CPPEXPORT StGLUVSphere(const StGLVec3& theCenter,
11
const GLfloat theRadius,
12
- const size_t theRings);
13
+ const size_t theRings,
14
+ const bool theIsHemisphere);
15
16
/**
17
* Defines the UV sphere from boundary sphere.
18
19
StGLVec3 myCenter;
20
GLfloat myRadius;
21
size_t myRings;
22
+ bool myIsHemisphere;
23
24
};
25
26
sview-17_04.tar.gz/include/StGLStereo/StFormatEnum.h -> sview-20_08.tar.gz/include/StGLStereo/StFormatEnum.h
Changed
63
1
2
/**
3
- * Copyright © 2009-2015 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2009-2019 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* Distributed under the Boost Software License, Version 1.0.
7
* See accompanying file license-boost.txt or copy at
8
9
enum StCubemap {
10
StCubemap_AUTO = -1, //!< try to detect from metadata
11
StCubemap_OFF = 0, //!< no cubemap data
12
- StCubemap_Packed //!< cubemap data packed into single image frame - 6 horizontally stacked planes
13
+ StCubemap_Packed, //!< cubemap data packed into single image frame - 6 horizontally stacked planes
14
+ StCubemap_PackedEAC //!< cubemap data packed into single image frame (EAC layout)
15
};
16
17
enum StPanorama {
18
- StPanorama_OFF = 0, //!< no cubemap data
19
- StPanorama_Sphere, //!< spherical panorama
20
- StPanorama_Cubemap6_1, //!< cubemap data packed into single image frame - 6:1
21
- StPanorama_Cubemap3_2 //!< cubemap data packed into single image frame - 3:2
22
+ StPanorama_OFF = 0, //!< no cubemap data
23
+ StPanorama_Sphere, //!< spherical panorama 360 degrees - 2:1
24
+ StPanorama_Hemisphere, //!< spherical panorama 180 degrees - 1:1
25
+ StPanorama_Cubemap6_1, //!< cubemap data packed into single image frame - 6:1 in OpenGL enum order (px nx py ny pz nz)
26
+ StPanorama_Cubemap1_6, //!< cubemap data packed into single image frame - 1:6 in OpenGL enum order
27
+ StPanorama_Cubemap3_2, //!< cubemap data packed into single image frame - 3:2 in OpenGL enum order
28
+ StPanorama_Cubemap3_2ytb, //!< cubemap data packed into single image frame - 3:2 in custom order (px nz nx, ny pz py)
29
+ //! one row defines 3 horizontally stacked sides of the cube, and other 3 vertically stacked sides
30
+ StPanorama_Cubemap2_3ytb //!< cubemap data packed into single image frame - 2:3 in custom order (90 counterclockwise transposed 3x2 layout)
31
};
32
33
namespace st {
34
35
* - half,q Anamorph suffix
36
* or file extension:
37
* - jps,pns SideBySide (Right/Left order)
38
+ * @param theFileName [in] file name to parse
39
+ * @param theToSwapJps [in] if TRUE, then JPS/PNS file extension will be treated as Left/Right instead of Right/Left
40
+ * @param theIsAnamorph [out] flag indicating anamorphic aspect ratio
41
*/
42
ST_CPPEXPORT StFormat formatFromName(const StString& theFileName,
43
+ const bool theToSwapJps,
44
bool& theIsAnamorph);
45
46
/**
47
48
} else if(theSrc1SizeX / 6 == theSrc1SizeY
49
&& theSrc2SizeX / 6 == theSrc2SizeY) {
50
return StPanorama_Cubemap6_1;
51
+ } else if(theSrc1SizeY / 6 == theSrc1SizeX
52
+ && theSrc2SizeY / 6 == theSrc2SizeX) {
53
+ return StPanorama_Cubemap1_6;
54
} else if(theSrc1SizeX / 3 == theSrc1SizeY / 2
55
&& theSrc2SizeX / 3 == theSrc2SizeY / 2) {
56
return StPanorama_Cubemap3_2;
57
+ } else if(theSrc1SizeX == theSrc1SizeY
58
+ && theSrc2SizeX == theSrc2SizeY) {
59
+ return StPanorama_Hemisphere;
60
}
61
return StPanorama_OFF;
62
}
63
sview-17_04.tar.gz/include/StGLStereo/StGLProjCamera.h -> sview-20_08.tar.gz/include/StGLStereo/StGLProjCamera.h
Changed
75
1
2
ST_CPPEXPORT StGLProjCamera();
3
4
/**
5
+ * Copy constructor.
6
+ */
7
+ ST_CPPEXPORT StGLProjCamera(const StGLProjCamera& theOther);
8
+
9
+ /**
10
* Custom projection camera.
11
*/
12
ST_CPPEXPORT StGLProjCamera(const GLfloat theFOVy,
13
14
const GLfloat theZScreen);
15
16
/**
17
+ * Copy camera settings.
18
+ */
19
+ ST_CPPEXPORT void copyFrom(const StGLProjCamera& theOther);
20
+
21
+ /**
22
+ * Copy camera settings.
23
+ */
24
+ ST_LOCAL StGLProjCamera& operator=(const StGLProjCamera& theOther) {
25
+ copyFrom(theOther);
26
+ return *this;
27
+ }
28
+
29
+ /**
30
* Get projection type.
31
*/
32
inline bool isPerspective() const {
33
34
*/
35
inline void setFOVy(const GLfloat theFOVy) {
36
myFOVy = theFOVy;
37
+ updateFrustum();
38
}
39
40
/**
41
42
}
43
44
/**
45
+ * Return TRUE if custom stereoscopic projection frustum has been set.
46
+ */
47
+ ST_LOCAL bool isCustomProjection() const { return myIsCustomFrust; }
48
+
49
+ /**
50
+ * Unset custom projection.
51
+ */
52
+ ST_CPPEXPORT void resetCustomProjection();
53
+
54
+ /**
55
+ * Setup custom projection.
56
+ */
57
+ ST_CPPEXPORT void setCustomProjection(const StRectF_t& theLeft, const StRectF_t& theRight);
58
+
59
+ /**
60
* Returns the string description for the camera.
61
* For debug purposes...
62
*/
63
64
65
StGLMatrix myMatrix; //!< current projection matrix
66
StGLMatrix myMatrixMono; //!< we store mono projection matrix to allow draw special object
67
+
68
+ StRectF_t myVrFrustumL; //!< custom VR projection frustum, left eye
69
+ StRectF_t myVrFrustumR; //!< custom VR projection frustum, right eye
70
+ bool myIsCustomFrust;
71
+
72
GLfloat myFOVy; //!< field of view in y-axis (degrees)
73
GLfloat myZoom; //!< linear zoom factor (changes the effective FOVy value!)
74
GLfloat myAspect; //!< screen aspect ratio, recomputed on window size change
75
sview-17_04.tar.gz/include/StGLStereo/StGLQuadTexture.h -> sview-20_08.tar.gz/include/StGLStereo/StGLQuadTexture.h
Changed
111
1
2
/**
3
- * Copyright © 2009-2013 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2009-2020 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* Distributed under the Boost Software License, Version 1.0.
7
* See accompanying file license-boost.txt or copy at
8
9
/**
10
* @return data size in the texture.
11
*/
12
- inline const StGLVec2& getDataSize() {
13
- return myDataSize;
14
- }
15
+ ST_LOCAL const StGLVec2& getDataSize() { return myDataSize; }
16
17
/**
18
- * @param theDataSize - setted data size in the texture.
19
+ * @param theDataSize - set data size in the texture.
20
*/
21
- inline void setDataSize(const StGLVec2& theDataSize) {
22
- myDataSize = theDataSize;
23
- }
24
+ ST_LOCAL void setDataSize(const StGLVec2& theDataSize) { myDataSize = theDataSize; }
25
26
/**
27
* @return display aspect ratio.
28
*/
29
- inline GLfloat getDisplayRatio() const {
30
- return myDisplayRatio;
31
- }
32
+ ST_LOCAL GLfloat getDisplayRatio() const { return myDisplayRatio; }
33
34
/**
35
* @param theValue - display aspect ratio.
36
*/
37
- inline void setDisplayRatio(const GLfloat theValue) {
38
- myDisplayRatio = theValue;
39
- }
40
+ ST_LOCAL void setDisplayRatio(const GLfloat theValue) { myDisplayRatio = theValue; }
41
+
42
+ /**
43
+ * Returns Pixel Aspect Ratio.
44
+ */
45
+ ST_LOCAL GLfloat getPixelRatio() const { return myPAR; }
46
+
47
+ /**
48
+ * Sets Pixel Aspect Ratio.
49
+ */
50
+ ST_LOCAL void setPixelRatio(const GLfloat thePAR) { myPAR = thePAR; }
51
+
52
+ /**
53
+ * Returns packed panorama format.
54
+ */
55
+ ST_LOCAL StPanorama getPackedPanorama() const { return myPanorama; }
56
+
57
+ /**
58
+ * Sets packed panorama format.
59
+ */
60
+ ST_LOCAL void setPackedPanorama(StPanorama thePano) { myPanorama = thePano; }
61
62
private:
63
64
- StGLVec2 myDataSize; //!< data size in the texture (x()=right and y()=bottom)
65
- GLfloat myDisplayRatio; //!< display aspect ratio
66
+ StGLVec2 myDataSize; //!< data size in the texture (x()=right and y()=bottom)
67
+ float myDisplayRatio; //!< display aspect ratio
68
+ float myPAR; //!< pixel aspect ratio
69
+ StPanorama myPanorama; //!< packed panorama format
70
71
};
72
73
74
* After this call current bound texture will be undefined.
75
*/
76
ST_CPPEXPORT void setMinMagFilter(StGLContext& theCtx,
77
- const GLenum theMinMagFilter);
78
+ const GLenum theMinFilter,
79
+ const GLenum theMagFilter);
80
+
81
+ /**
82
+ * Change Min and Mag filter.
83
+ * After this call current bound texture will be undefined.
84
+ */
85
+ ST_LOCAL void setMinMagFilter(StGLContext& theCtx,
86
+ const GLenum theMinMagFilter) {
87
+ setMinMagFilter(theCtx, theMinMagFilter, theMinMagFilter);
88
+ }
89
90
private:
91
92
93
* After this call current bound texture will be undefined.
94
*/
95
ST_CPPEXPORT void setMinMagFilter(StGLContext& theCtx,
96
- const GLenum theMinMagFilter);
97
+ const GLenum theMinFilter,
98
+ const GLenum theMagFilter);
99
+
100
+ /**
101
+ * Change Min and Mag filter.
102
+ * After this call current bound texture will be undefined.
103
+ */
104
+ ST_LOCAL void setMinMagFilter(StGLContext& theCtx,
105
+ const GLenum theMinMagFilter) {
106
+ setMinMagFilter(theCtx, theMinMagFilter, theMinMagFilter);
107
+ }
108
109
private:
110
111
sview-17_04.tar.gz/include/StGLStereo/StGLTextureData.h -> sview-20_08.tar.gz/include/StGLStereo/StGLTextureData.h
Changed
44
1
2
/**
3
- * Copyright © 2009-2016 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2009-2020 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* Distributed under the Boost Software License, Version 1.0.
7
* See accompanying file license-boost.txt or copy at
8
9
#define __StGLTextureData_h_
10
11
#include <StImage/StImage.h>
12
+#include <StGLStereo/StGLTextureUploadParams.h>
13
#include <StGLStereo/StGLQuadTexture.h>
14
#include <StGL/StGLDeviceCaps.h>
15
16
17
/**
18
* Default constructor
19
*/
20
- ST_CPPEXPORT StGLTextureData();
21
+ ST_CPPEXPORT StGLTextureData(const StHandle<StGLTextureUploadParams>& theUploadParams);
22
23
/**
24
* Destructor.
25
26
27
ST_LOCAL void setupAttributes(StGLFrameTextures& stFrameTextures, const StImage& theImage);
28
29
+ ST_LOCAL void setupDataRectangle(const StImagePlane& theImagePlane,
30
+ const GLfloat thePixelRatio,
31
+ StGLFrameTexture& theTextureFrame);
32
+
33
private:
34
35
StGLTextureData* myPrev; //!< pointer to previous item in the list
36
37
StFormat mySrcFormat;
38
StCubemap myCubemapFormat;
39
40
+ StHandle<StGLTextureUploadParams> myUploadParams; //!< texture streaming parameters
41
GLsizei myFillFromRow;
42
GLsizei myFillRows;
43
44
sview-17_04.tar.gz/include/StGLStereo/StGLTextureQueue.h -> sview-20_08.tar.gz/include/StGLStereo/StGLTextureQueue.h
Changed
43
1
2
ST_CPPEXPORT ~StGLTextureQueue();
3
4
/**
5
+ * Get device capabilities.
6
+ */
7
+ ST_LOCAL const StGLDeviceCaps& getDeviceCaps() const { return myDeviceCaps; }
8
+
9
+ /**
10
* Set device capabilities.
11
*/
12
ST_LOCAL void setDeviceCaps(const StGLDeviceCaps& theCaps) {
13
14
}
15
16
/**
17
+ * Return texture streaming parameters.
18
+ */
19
+ ST_LOCAL StGLTextureUploadParams& getUploadParams() { return *myUploadParams; }
20
+
21
+ /**
22
* @return input stream connection state
23
*/
24
ST_LOCAL bool hasConnectedStream() const {
25
26
* This function clean up only requested number of frames but prevents queue emptying.
27
* At least one frame will remain in queue.
28
*/
29
- ST_CPPEXPORT void drop(const size_t theCount);
30
+ ST_CPPEXPORT void drop(const size_t theCount,
31
+ double& thePtsFront);
32
33
/**
34
* Function used to get current showed source format.
35
36
volatile bool myHasStream; //!< flag indicates that some stream connected to this queue
37
38
StGLDeviceCaps myDeviceCaps; //!< device capabilities
39
+ StHandle<StGLTextureUploadParams> myUploadParams; //!< texture streaming parameters
40
41
};
42
43
sview-20_08.tar.gz/include/StGLStereo/StGLTextureUploadParams.h
Added
41
1
2
+/**
3
+ * Copyright © 2019 Kirill Gavrilov <kirill@sview.ru>
4
+ *
5
+ * Distributed under the Boost Software License, Version 1.0.
6
+ * See accompanying file license-boost.txt or copy at
7
+ * http://www.boost.org/LICENSE_1_0.txt
8
+ */
9
+
10
+#ifndef __StGLTextureUploadParams_h_
11
+#define __StGLTextureUploadParams_h_
12
+
13
+/**
14
+ * Structure holding parameters for texture uploading.
15
+ * Uploading big amounts of data onto GPU leads to frame-rate lags (specifically in case when uploading done within rendering thread);
16
+ * to smooth this effect, upload process can be split into smaller chunks.
17
+ *
18
+ * There are 4 use cases, which are sensitive to texture uploading lags:
19
+ * - GUI rendering; will be noticeable only for very large uploads.
20
+ * - 360 panorama with device orientation tracking; will be noticeable due lag on orientation update.
21
+ * - HMD output with head orientation tracking; same as panorama, but will be noticeable all time (no option disabling head tracking) and can lead to headaches.
22
+ * - Software PageFlipping (texture uploading lag might lead to missing VSync and swapping Left/Right frames).
23
+ *
24
+ * Most optimal case would be defining amount of chunks equal to amount of frames to be rendered before new (uploaded) texture should appear,
25
+ * in this case average FPS will be close to constant, which is in particular good to preserve GUI interactive.
26
+ * At the same time, uploading data within more than 1 rendering frame would add a constant time shift to video stream presented to user,
27
+ * which ideally should be also considered.
28
+ * At last, the real maximum rendering FPS naturally limited by monitor frequency, can be not achievable due to slow GPU.
29
+ */
30
+struct StGLTextureUploadParams {
31
+
32
+ int MaxUploadIterations; //!< maximum number of texture upload iterations (frames); 1 means texture should be uploaded immediately
33
+ int MaxUploadChunkMiB; //!< maximum number of data in MiB to be uploaded within single iteration; 0 means no limit;
34
+ //! MaxUploadIterations is stronger limit
35
+
36
+ StGLTextureUploadParams() : MaxUploadIterations(1), MaxUploadChunkMiB(0) {}
37
+
38
+};
39
+
40
+#endif // __StGLTextureUploadParams_h_
41
sview-17_04.tar.gz/include/StGLWidgets/StGLCombobox.h -> sview-20_08.tar.gz/include/StGLWidgets/StGLCombobox.h
Changed
9
1
2
/**
3
* StGLWidgets, small C++ toolkit for writing GUI using OpenGL.
4
- * Copyright © 2015 Kirill Gavrilov <kirill@sview.ru>
5
+ * Copyright © 2015-2020 Kirill Gavrilov <kirill@sview.ru>
6
*
7
* Distributed under the Boost Software License, Version 1.0.
8
* See accompanying file license-boost.txt or copy at
9
sview-17_04.tar.gz/include/StGLWidgets/StGLImageProgram.h -> sview-20_08.tar.gz/include/StGLWidgets/StGLImageProgram.h
Changed
135
1
2
/**
3
* StGLWidgets, small C++ toolkit for writing GUI using OpenGL.
4
- * Copyright © 2010-2017 Kirill Gavrilov <kirill@sview.ru>
5
+ * Copyright © 2010-2019 Kirill Gavrilov <kirill@sview.ru>
6
*
7
* Distributed under the Boost Software License, Version 1.0.
8
* See accompanying file license-boost.txt or copy at
9
10
/**
11
* GLSL program for Image Region widget.
12
*/
13
-class StGLImageProgram : public StGLProgramMatrix<1, 5, StGLMeshProgram> {
14
+class StGLImageProgram : public StGLProgramMatrix<1, 6, StGLMeshProgram> {
15
16
public:
17
18
typedef enum tagTextureFilter {
19
- FILTER_NEAREST, //!< ugly filter
20
- FILTER_LINEAR, //!< linear filter
21
- FILTER_BLEND, //!< blend deinterlace filter
22
+ FILTER_NEAREST, //!< ugly filter
23
+ FILTER_LINEAR, //!< linear filter
24
+ FILTER_BLEND, //!< blend deinterlace filter
25
+ FILTER_TRILINEAR, //!< trilinear filter (generate mip-maps)
26
} TextureFilter;
27
28
/**
29
30
* Color conversion options in GLSL Fragment Shader.
31
*/
32
enum FragSection {
33
- FragSection_Main = 0, //!< section with main() function
34
- FragSection_GetColor, //!< read color values from textures
35
- FragSection_ToRgb, //!< color conversion
36
- FragSection_Correct, //!< color correction
37
- FragSection_Gamma, //!< gamma correction
38
+ FragSection_Main = 0, //!< section with main() function
39
+ FragSection_GetColor, //!< read color values from textures
40
+ FragSection_GetTexCoords, //!< EAC texture coordinates correction
41
+ FragSection_ToRgb, //!< color conversion
42
+ FragSection_Correct, //!< color correction
43
+ FragSection_Gamma, //!< gamma correction
44
FragSection_NB
45
};
46
47
48
FragToRgb_FromGray,
49
FragToRgb_FromXyz,
50
FragToRgb_FromYuvFull,
51
+ FragToRgb_FromYuvaFull,
52
FragToRgb_FromYuvMpeg,
53
+ FragToRgb_FromYuvaMpeg,
54
FragToRgb_FromYuv9Full,
55
+ FragToRgb_FromYuva9Full,
56
FragToRgb_FromYuv9Mpeg,
57
+ FragToRgb_FromYuva9Mpeg,
58
FragToRgb_FromYuv10Full,
59
+ FragToRgb_FromYuva10Full,
60
FragToRgb_FromYuv10Mpeg,
61
+ FragToRgb_FromYuva10Mpeg,
62
FragToRgb_FromYuvNvFull,
63
FragToRgb_FromYuvNvMpeg,
64
FragToRgb_CUBEMAP,
65
66
FragGamma_NB
67
};
68
69
+ /**
70
+ * Texture coordinates EAC correction options in GLSL Fragment Shader.
71
+ */
72
+ enum FragTexEAC {
73
+ FragTexEAC_Off = 0,
74
+ FragTexEAC_On,
75
+ FragTexEAC_NB
76
+ };
77
+
78
public:
79
80
ST_CPPEXPORT StGLImageProgram();
81
82
ST_CPPEXPORT void setTextureUVDataSize(StGLContext& theCtx,
83
const StGLVec4& theTexDataVec4);
84
85
+ ST_CPPEXPORT void setTextureADataSize(StGLContext& theCtx,
86
+ const StGLVec4& theTexDataVec4);
87
+
88
ST_CPPEXPORT void setCubeTextureFlipZ(StGLContext& theCtx,
89
bool theToFlip);
90
91
92
/**
93
* Initialize default shaders, nothing more.
94
*/
95
- ST_CPPEXPORT virtual bool init(StGLContext& theCtx,
96
- const StImage::ImgColorModel theColorModel,
97
- const StImage::ImgColorScale theColorScale,
98
- const FragGetColor theFilter);
99
+ ST_CPPEXPORT bool init(StGLContext& theCtx,
100
+ const StImage::ImgColorModel theColorModel,
101
+ const StImage::ImgColorScale theColorScale,
102
+ const FragGetColor theFilter,
103
+ const FragTexEAC theTexCoord = FragTexEAC_Off);
104
105
public: //!< Properties
106
107
108
private: //!< callback Slots
109
110
ST_LOCAL void setupCorrection(StGLContext& theCtx);
111
- ST_LOCAL void regToRgb(const int thePartIndex,
112
+ ST_LOCAL void regToRgb(const StGLContext& theCtx,
113
+ const int thePartIndex,
114
const StString& theText);
115
+ ST_LOCAL void registerFragments(const StGLContext& theCtx);
116
117
protected:
118
119
120
121
StGLVarLocation uniTexMainDataLoc;
122
StGLVarLocation uniTexUVDataLoc;
123
+ StGLVarLocation uniTexADataLoc;
124
StGLVarLocation uniTexSizePxLoc;
125
StGLVarLocation uniTexelSizePxLoc;
126
StGLVarLocation uniTexCubeFlipZLoc;
127
128
StGLVarLocation uniGammaLoc;
129
130
StGLVec3 myColorScale; //!< scale filter for de-anaglyph processing
131
+ bool myIsRegistered;
132
133
};
134
135
sview-17_04.tar.gz/include/StGLWidgets/StGLImageRegion.h -> sview-20_08.tar.gz/include/StGLWidgets/StGLImageRegion.h
Changed
137
1
2
/**
3
* StGLWidgets, small C++ toolkit for writing GUI using OpenGL.
4
- * Copyright © 2010-2016 Kirill Gavrilov <kirill@sview.ru>
5
+ * Copyright © 2010-2020 Kirill Gavrilov <kirill@sview.ru>
6
*
7
* Distributed under the Boost Software License, Version 1.0.
8
* See accompanying file license-boost.txt or copy at
9
10
#ifndef __StGLImageRegion_h_
11
#define __StGLImageRegion_h_
12
13
+#include <StGLMesh/StGLUVCylinder.h>
14
#include <StGLMesh/StGLUVSphere.h>
15
#include <StGLMesh/StGLQuads.h>
16
17
18
#include <StGLStereo/StGLTextureQueue.h>
19
20
#include <StGL/StParams.h>
21
+#include <StGL/StPlayList.h>
22
23
+#include <StSlots/StAction.h>
24
#include <StSettings/StEnumParam.h>
25
26
-class StAction;
27
+class StGLIcon;
28
29
class StGLImageRegion : public StGLWidget {
30
31
32
const bool theUsePanningKeys);
33
34
/**
35
+ * Return playlist.
36
+ */
37
+ ST_LOCAL const StHandle<StPlayList>& getPlayList() const {
38
+ return myList;
39
+ }
40
+
41
+ /**
42
+ * Set playlist.
43
+ */
44
+ ST_LOCAL void setPlayList(const StHandle<StPlayList>& theList) {
45
+ myList = theList;
46
+ }
47
+
48
+ /**
49
+ * Return icon widget displayed on swipe gesture.
50
+ */
51
+ StGLIcon* changeIconPrev() { return myIconPrev; }
52
+
53
+ /**
54
+ * Return icon widget displayed on swipe gesture.
55
+ */
56
+ StGLIcon* changeIconNext() { return myIconNext; }
57
+
58
+ /**
59
* Setup device orientation.
60
*/
61
ST_LOCAL void setDeviceOrientation(const StGLQuaternion& theQ) { myDeviceQuat = theQ; }
62
63
*/
64
ST_CPPEXPORT void stglSkipFrames();
65
66
+ /**
67
+ * Return sample aspect ratio.
68
+ */
69
+ ST_LOCAL float getSampleRatio() const { return mySampleRatio; }
70
+
71
+ /**
72
+ * Return frame dimensions.
73
+ */
74
+ ST_LOCAL const StVec2<int>& getFrameSize() const { return myFrameSize; }
75
+
76
public: //! @name Properties
77
78
struct {
79
80
81
} params;
82
83
+ public: //! @name Signals
84
+
85
+ struct {
86
+ /**
87
+ * Emit new item signal.
88
+ */
89
+ StSignal<void (void )> onOpenItem;
90
+ } signals;
91
+
92
private:
93
94
/**
95
96
97
ST_LOCAL void doRightUnclick(const StPointD_t& theCursorZo);
98
99
+ ST_LOCAL bool stglInitCube(const StGLVec4& theClampUV = StGLVec4(0.0f, 0.0f, 1.0f, 1.0f),
100
+ const StPanorama thePano = StPanorama_OFF);
101
ST_LOCAL void stglDrawView(unsigned int theView);
102
103
private: //! @name private fields
104
105
StArrayList< StHandle<StAction> >
106
myActions; //!< actions list
107
+ StHandle<StPlayList> myList; //!< handle to playlist
108
+
109
+ StGLIcon* myIconPrev; //!< icon displayed on swipe gesture
110
+ StGLIcon* myIconNext; //!< icon displayed on swipe gesture
111
112
StGLQuads myQuad; //!< flat quad
113
- StGLUVSphere myUVSphere; //!< sphere output helper class
114
+ StGLMesh myCube; //!< cube for drawing cubemap
115
+ StGLVec4 myCubeClamp; //!< cubemap clamping vector
116
+ StPanorama myCubePano; //!< cubemap panorama format
117
+ StGLUVSphere myUVSphere; //!< sphere mesh object
118
+ StGLUVSphere myHemisphere; //!< hemisphere mesh object
119
+ StGLUVCylinder myCylinder; //!< cylinder mesh object
120
+ StGLUVCylinder myTheater; //!< theater cylinder mesh object
121
StGLProjCamera myProjCam; //!< copy of projection camera
122
StGLImageProgram myProgram; //!< GL program to draw flat image
123
StHandle<StGLTextureQueue> myTextureQueue; //!< shared texture queue
124
StPointD_t myClickPntZo; //!< remembered mouse click position
125
StTimer myClickTimer; //!< timer to delay dragging action
126
+ StTimer myFadeTimer; //!< timer for transition to the next file
127
+ StPointD_t myFadeFrom; //!< fade starting delta
128
StGLQuaternion myDeviceQuat; //!< device orientation
129
StVirtFlags myKeyFlags; //!< active key flags
130
double myDragDelayMs; //!< dragging delay in milliseconds
131
+ double myDragDelayTmpMs; //!< temporary dragging delay
132
+ StVec2<int> myFrameSize; //!< frame dimensions
133
+ float mySampleRatio; //!< sample aspect ratio
134
float myRotAngle; //!< rotation angle gesture progress
135
bool myIsClickAborted;
136
bool myToRightRotate;
137
sview-17_04.tar.gz/include/StGLWidgets/StGLMenuCheckbox.h -> sview-20_08.tar.gz/include/StGLWidgets/StGLMenuCheckbox.h
Changed
13
1
2
ST_CPPEXPORT StGLMenuCheckbox(StGLMenu* theParent,
3
const StHandle<StBoolParam>& theTrackedValue);
4
5
+ /**
6
+ * Return checkbox widget.
7
+ */
8
+ StGLCheckbox* getCheckbox() { return myCheckbox; }
9
+
10
private: //!< callback Slots (private overriders)
11
12
ST_LOCAL void doItemClick(const size_t );
13
sview-17_04.tar.gz/include/StGLWidgets/StGLMessageBox.h -> sview-20_08.tar.gz/include/StGLWidgets/StGLMessageBox.h
Changed
22
1
2
const bool theIsDefault = false,
3
const int theWidth = 0);
4
5
- ST_CPPEXPORT virtual bool doKeyDown(const StKeyEvent& theEvent);
6
+ ST_CPPEXPORT virtual bool doKeyDown(const StKeyEvent& theEvent) ST_ATTR_OVERRIDE;
7
8
ST_LOCAL int getMarginLeft() const { return myMarginLeft; }
9
ST_LOCAL int getMarginRight() const { return myMarginRight; }
10
11
*/
12
ST_CPPEXPORT void create(const StString& theTitle,
13
const StString& theText,
14
- const int theWidth,
15
- const int theHeight);
16
+ const int theWidth,
17
+ const int theHeight,
18
+ const bool theHasButtons = true);
19
20
private: //! @name callback Slots (private overriders)
21
22
sview-17_04.tar.gz/include/StGLWidgets/StGLOpenFile.h -> sview-20_08.tar.gz/include/StGLWidgets/StGLOpenFile.h
Changed
94
1
2
/**
3
* StGLWidgets, small C++ toolkit for writing GUI using OpenGL.
4
- * Copyright © 2015 Kirill Gavrilov <kirill@sview.ru>
5
+ * Copyright © 2015-2019 Kirill Gavrilov <kirill@sview.ru>
6
*
7
* Distributed under the Boost Software License, Version 1.0.
8
* See accompanying file license-boost.txt or copy at
9
10
#include <StGLWidgets/StGLMessageBox.h>
11
#include <StGLWidgets/StGLRootWidget.h>
12
#include <StFile/StMIMEList.h>
13
+#include <StSettings/StParam.h>
14
15
class StGLMenu;
16
class StGLMenuItem;
17
+class StGLMenuCheckbox;
18
19
/**
20
* Widget for file system navigation.
21
22
/**
23
* Define file filter.
24
*/
25
- ST_CPPEXPORT void setMimeList(const StMIMEList& theFilter);
26
+ ST_CPPEXPORT void setMimeList(const StMIMEList& theFilter,
27
+ const StString& theName = "",
28
+ const bool theIsExtra = false);
29
30
/**
31
- * Open new folder.
32
+ * Check/uncheck extra files.
33
+ */
34
+ ST_LOCAL void setDisplayExtra(bool theToDisplay) {
35
+ myToShowExtraFilter->setValue(theToDisplay);
36
+ }
37
+
38
+ /**
39
+ * Add checkbox.
40
+ */
41
+ ST_CPPEXPORT StGLMenuCheckbox* addHotCheckbox(const StHandle<StBoolParam>& theParam,
42
+ const StString& theName);
43
+
44
+ /**
45
+ * Add system drives to folders' list.
46
+ */
47
+ ST_CPPEXPORT void addSystemDrives();
48
+
49
+ /**
50
+ * Add item to folders' list.
51
*/
52
ST_CPPEXPORT void addHotItem(const StString& theTarget,
53
const StString& theName = "");
54
55
ST_CPPEXPORT void doHotItemClick(const size_t theItemId);
56
57
/**
58
+ * Handle filter check.
59
+ */
60
+ ST_CPPEXPORT void doFilterCheck(const bool theIsChecked);
61
+
62
+ /**
63
* Handle item click event - just remember item id.
64
*/
65
ST_CPPEXPORT void doFileItemClick(const size_t theItemId);
66
67
ST_CPPEXPORT virtual bool tryUnClick(const StClickEvent& theEvent,
68
bool& theIsItemUnclicked) ST_ATTR_OVERRIDE;
69
70
+ /**
71
+ * Reset extension list.
72
+ */
73
+ ST_CPPEXPORT void initExtensions();
74
+
75
protected: //! @name class fields
76
77
StHandle<StGLTextureArray> myTextureFolder;
78
StHandle<StGLTextureArray> myTextureFile;
79
StGLTextArea* myCurrentPath;
80
+ StGLScrollArea* myHotListContent;
81
StGLMenu* myHotList; //!< widget containing the list of predefined libraries
82
StGLMenu* myList; //!< widget containing the file list of currently opened folder
83
+ StGLMenuCheckbox* myMainFilterCheck; //!< main file filter checkbox
84
+ StGLMenuCheckbox* myExtraFilterCheck; //!< extra file filter checkbox
85
+ StHandle<StBoolParam> myToShowMainFilter;
86
+ StHandle<StBoolParam> myToShowExtraFilter;
87
StArrayList<StString> myHotPaths; //!< array of hot-links
88
StHandle<StFolder> myFolder; //!< currently opened folder
89
StMIMEList myFilter; //!< file filter
90
+ StMIMEList myExtraFilter; //!< extra file filter
91
StArrayList<StString> myExtensions; //!< extensions filter
92
StString myItemToLoad; //!< new item to open
93
94
sview-17_04.tar.gz/include/StGLWidgets/StGLRootWidget.h -> sview-20_08.tar.gz/include/StGLWidgets/StGLRootWidget.h
Changed
60
1
2
/**
3
* StGLWidgets, small C++ toolkit for writing GUI using OpenGL.
4
- * Copyright © 2009-2017 Kirill Gavrilov <kirill@sview.ru>
5
+ * Copyright © 2009-2020 Kirill Gavrilov <kirill@sview.ru>
6
*
7
* Distributed under the Boost Software License, Version 1.0.
8
* See accompanying file license-boost.txt or copy at
9
10
return myScrDispX;
11
}
12
13
- inline GLfloat getLensDist() const {
14
- return myLensDist;
15
- }
16
-
17
inline void setLensDist(const GLfloat theLensDist) {
18
myLensDist = theLensDist;
19
}
20
21
* @param theRect Rectangle in window coordinates
22
* @param theScissorRect Scissor rectangle for glScissor() call
23
*/
24
- ST_CPPEXPORT void stglScissorRect(const StRectI_t& theRect,
25
- StGLBoxPx& theScissorRect) const;
26
+ ST_LOCAL void stglScissorRect2d(const StRectI_t& theRect,
27
+ StGLBoxPx& theScissorRect) const {
28
+ stglScissorRectInternal(theRect, true, theScissorRect);
29
+ }
30
+
31
+ /**
32
+ * Computes scissor rectangle in OpenGL viewport.
33
+ * @param theRect Rectangle in window coordinates
34
+ * @param theScissorRect Scissor rectangle for glScissor() call
35
+ */
36
+ ST_LOCAL void stglScissorRect3d(const StRectI_t& theRect,
37
+ StGLBoxPx& theScissorRect) const {
38
+ stglScissorRectInternal(theRect, false, theScissorRect);
39
+ }
40
41
/**
42
* Append widget to destroy list.
43
44
45
ST_LOCAL void setupTextures();
46
47
+ /**
48
+ * Computes scissor rectangle in OpenGL viewport.
49
+ * @param theRect [in] Rectangle in window coordinates
50
+ * @param theIs2d [in] 2d/3d flag
51
+ * @param theScissorRect [out] Scissor rectangle for glScissor() call
52
+ */
53
+ ST_CPPEXPORT void stglScissorRectInternal(const StRectI_t& theRect,
54
+ const bool theIs2d,
55
+ StGLBoxPx& theScissorRect) const;
56
+
57
private:
58
59
StGLSharePointer** myShareArray; //!< resources shared within GL context (commonly used)
60
sview-17_04.tar.gz/include/StGLWidgets/StGLScrollArea.h -> sview-20_08.tar.gz/include/StGLWidgets/StGLScrollArea.h
Changed
21
1
2
}
3
4
/**
5
+ * Returns TRUE if dragging has been confirmed.
6
+ */
7
+ ST_LOCAL bool hasDragged() const { return myHasDragged; }
8
+
9
+ /**
10
* Scroll (vertically) content.
11
* @param theDelta scroll delta
12
* @return true if scrolling has been done
13
14
StTimer myFlingTimer; //!< timer for dragging inertia
15
double myFlingYSpeed; //!< the dragging velocity for inertial scrolling
16
int myFlingYDone; //!< already animated inertial scrolling
17
+ float myScrollYAccum;//!< accumulated scroll event value
18
19
};
20
21
sview-17_04.tar.gz/include/StGLWidgets/StGLSubtitles.h -> sview-20_08.tar.gz/include/StGLWidgets/StGLSubtitles.h
Changed
79
1
2
/**
3
* StGLWidgets, small C++ toolkit for writing GUI using OpenGL.
4
- * Copyright © 2010-2015 Kirill Gavrilov <kirill@sview.ru>
5
+ * Copyright © 2010-2020 Kirill Gavrilov <kirill@sview.ru>
6
*
7
* Distributed under the Boost Software License, Version 1.0.
8
* See accompanying file license-boost.txt or copy at
9
10
template<>
11
inline void StArray<StHandle <StSubItem> >::sort() {}
12
13
+class StGLImageRegion;
14
+
15
/**
16
* Subtitles widget.
17
*/
18
19
20
StString Text; //!< active string representation
21
StImagePlane Image; //!< active image representation
22
+ float Scale; //!< image scale factor
23
24
public:
25
26
27
28
public:
29
30
- ST_CPPEXPORT StGLSubtitles(StGLWidget* theParent,
31
+ /**
32
+ * Main constructor.
33
+ */
34
+ ST_CPPEXPORT StGLSubtitles(StGLImageRegion* theParent,
35
const StHandle<StSubQueue>& theSubQueue,
36
const StHandle<StInt32Param>& thePlace,
37
- const StHandle<StFloat32Param>& theTopDY,
38
- const StHandle<StFloat32Param>& theBottomDY,
39
- const StHandle<StFloat32Param>& theFontSize,
40
- const StHandle<StFloat32Param>& theParallax,
41
- const StHandle<StEnumParam>& theParser);
42
+ const StHandle<StFloat32Param>& theFontSize);
43
+
44
+ /**
45
+ * Destructor.
46
+ */
47
ST_CPPEXPORT virtual ~StGLSubtitles();
48
ST_CPPEXPORT virtual bool stglInit() ST_ATTR_OVERRIDE;
49
ST_CPPEXPORT virtual void stglUpdate(const StPointD_t& thePointZo,
50
51
*/
52
ST_CPPEXPORT void setPTS(const double thePTS);
53
54
+ public: //! @name Properties
55
+
56
+ struct {
57
+
58
+ StHandle<StInt32Param> Place; //!< placement
59
+ StHandle<StFloat32Param> TopDY; //!< displacement
60
+ StHandle<StFloat32Param> BottomDY; //!< displacement
61
+ StHandle<StFloat32Param> FontSize; //!< font size parameter
62
+ StHandle<StFloat32Param> Parallax; //!< text parallax
63
+ StHandle<StEnumParam> Parser; //!< text parser option
64
+ StHandle<StBoolParamNamed> ToApplyStereo; //!< apply stereoscopic format of video to image subtitles
65
+
66
+ } params;
67
+
68
private:
69
70
- StHandle<StInt32Param> myPlace; //!< placement
71
- StHandle<StFloat32Param> myTopDY; //!< displacement
72
- StHandle<StFloat32Param> myBottomDY; //!< displacement
73
- StHandle<StFloat32Param> myFontSize; //!< font size parameter
74
- StHandle<StFloat32Param> myParallax; //!< text parallax
75
- StHandle<StEnumParam> myParser; //!< text parser option
76
StGLTexture myTexture; //!< texture for image-based subtitles
77
StGLVertexBuffer myVertBuf; //!< vertex buffer for image-based subtitles
78
StGLVertexBuffer myTCrdBuf; //!< texture coordinates buffer for image-based subtitles
79
sview-17_04.tar.gz/include/StGLWidgets/StGLTable.h -> sview-20_08.tar.gz/include/StGLWidgets/StGLTable.h
Changed
9
1
2
/**
3
* StGLWidgets, small C++ toolkit for writing GUI using OpenGL.
4
- * Copyright © 2014-2015 Kirill Gavrilov <kirill@sview.ru>
5
+ * Copyright © 2014-2017 Kirill Gavrilov <kirill@sview.ru>
6
*
7
* Distributed under the Boost Software License, Version 1.0.
8
* See accompanying file license-boost.txt or copy at
9
sview-17_04.tar.gz/include/StGLWidgets/StGLTextArea.h -> sview-20_08.tar.gz/include/StGLWidgets/StGLTextArea.h
Changed
9
1
2
/**
3
* StGLWidgets, small C++ toolkit for writing GUI using OpenGL.
4
- * Copyright © 2009-2017 Kirill Gavrilov <kirill@sview.ru>
5
+ * Copyright © 2009-2020 Kirill Gavrilov <kirill@sview.ru>
6
*
7
* Distributed under the Boost Software License, Version 1.0.
8
* See accompanying file license-boost.txt or copy at
9
sview-17_04.tar.gz/include/StGLWidgets/StGLTextBorderProgram.h -> sview-20_08.tar.gz/include/StGLWidgets/StGLTextBorderProgram.h
Changed
38
1
2
/**
3
* StGLWidgets, small C++ toolkit for writing GUI using OpenGL.
4
- * Copyright © 2009-2015 Kirill Gavrilov <kirill@sview.ru>
5
+ * Copyright © 2009-2020 Kirill Gavrilov <kirill@sview.ru>
6
*
7
* Distributed under the Boost Software License, Version 1.0.
8
* See accompanying file license-boost.txt or copy at
9
10
const StGLMatrix& theProjMat);
11
12
/**
13
- * Setup model-view matrix.
14
- * @param theCtx active GL context
15
- * @param theModelMat model-view matrix
16
+ * Setup components of model-view matrix.
17
+ * @param theCtx active GL context
18
+ * @param theDisp translation vector
19
+ * @param theScale scale factor
20
*/
21
- ST_CPPEXPORT void setModelMat(StGLContext& theCtx,
22
- const StGLMatrix& theModelMat);
23
+ ST_CPPEXPORT void setDisplacement(StGLContext& theCtx,
24
+ const StGLVec3& theDisp,
25
+ const float theScale);
26
27
/**
28
* Setup text color.
29
30
private:
31
32
StGLVarLocation myUniformProjMat; //!< location of uniform variable of projection matrix
33
- StGLVarLocation myUniformModelMat; //!< location of uniform variable of model view matrix
34
+ StGLVarLocation myUniformDispl; //!< location of uniform variable of displacement vector
35
StGLVarLocation myUniformColor; //!< location of uniform variable of color value
36
37
};
38
sview-17_04.tar.gz/include/StGLWidgets/StGLTextProgram.h -> sview-20_08.tar.gz/include/StGLWidgets/StGLTextProgram.h
Changed
38
1
2
/**
3
* StGLWidgets, small C++ toolkit for writing GUI using OpenGL.
4
- * Copyright © 2009-2015 Kirill Gavrilov <kirill@sview.ru>
5
+ * Copyright © 2009-2020 Kirill Gavrilov <kirill@sview.ru>
6
*
7
* Distributed under the Boost Software License, Version 1.0.
8
* See accompanying file license-boost.txt or copy at
9
10
const StGLMatrix& theProjMat);
11
12
/**
13
- * Setup model-view matrix.
14
- * @param theCtx active GL context
15
- * @param theModelMat model-view matrix
16
+ * Setup components of model-view matrix.
17
+ * @param theCtx active GL context
18
+ * @param theDisp translation vector
19
+ * @param theScale scale factor
20
*/
21
- ST_CPPEXPORT void setModelMat(StGLContext& theCtx,
22
- const StGLMatrix& theModelMat);
23
+ ST_CPPEXPORT void setDisplacement(StGLContext& theCtx,
24
+ const StGLVec3& theDisp,
25
+ const float theScale);
26
27
/**
28
* Setup text color.
29
30
private:
31
32
StGLVarLocation myUniformProjMat; //!< location of uniform variable of projection matrix
33
- StGLVarLocation myUniformModelMat; //!< location of uniform variable of model view matrix
34
+ StGLVarLocation myUniformDispl; //!< location of uniform variable of displacement vector
35
StGLVarLocation myUniformColor; //!< location of uniform variable of color value
36
37
};
38
sview-17_04.tar.gz/include/StGLWidgets/StGLWidget.h -> sview-20_08.tar.gz/include/StGLWidgets/StGLWidget.h
Changed
27
1
2
*/
3
ST_CPPEXPORT double perform(bool theDirUp, bool theToForce);
4
5
+ /**
6
+ * Return value within 0.0 - 1.0 range.
7
+ */
8
+ double getValue() const { return myValue; }
9
+
10
private:
11
12
double myValue; //!< value within 0.0 - 1.0 range
13
14
/**
15
* @param theScissorRect rectangle for OpenGL scissor test
16
*/
17
- ST_CPPEXPORT void stglScissorRect(StGLBoxPx& theScissorRect) const;
18
+ ST_CPPEXPORT void stglScissorRect2d(StGLBoxPx& theScissorRect) const;
19
+
20
+ /**
21
+ * @param theScissorRect rectangle for OpenGL scissor test
22
+ */
23
+ ST_CPPEXPORT void stglScissorRect3d(StGLBoxPx& theScissorRect) const;
24
25
/**
26
* @param thePointZo point in Zero2One coordinates to convert
27
sview-17_04.tar.gz/include/StGLWidgets/StSubQueue.h -> sview-20_08.tar.gz/include/StGLWidgets/StSubQueue.h
Changed
20
1
2
StImagePlane Image; //!< subtitle image representation
3
double TimeStart; //!< PTS to show subtitle item
4
double TimeEnd; //!< PTS to hide subtitle item
5
+ float Scale; //!< image scale factor
6
7
public:
8
9
- ST_LOCAL StSubItem(const double theTimeStart,
10
- const double theTimeEnd)
11
+ ST_LOCAL StSubItem(double theTimeStart,
12
+ double theTimeEnd)
13
: TimeStart(theTimeStart),
14
- TimeEnd(theTimeEnd) {
15
+ TimeEnd(theTimeEnd),
16
+ Scale(1.0f) {
17
//
18
}
19
20
sview-17_04.tar.gz/include/StImage/StDevILImage.h -> sview-20_08.tar.gz/include/StImage/StDevILImage.h
Changed
10
1
2
ST_CPPEXPORT StDevILImage();
3
ST_CPPEXPORT virtual ~StDevILImage();
4
5
+ ST_LOCAL virtual StHandle<StImageFile> createEmpty() const ST_ATTR_OVERRIDE { return new StDevILImage(); }
6
+
7
ST_CPPEXPORT virtual void close() ST_ATTR_OVERRIDE;
8
ST_CPPEXPORT virtual bool loadExtra(const StString& theFilePath,
9
ImageType theImageType,
10
sview-17_04.tar.gz/include/StImage/StExifDir.h -> sview-20_08.tar.gz/include/StImage/StExifDir.h
Changed
15
1
2
Entry.Components = 0;
3
}
4
5
- Query(DirType theType, uint16_t theTag) : Type(theType), Folder(NULL) {
6
+ Query(DirType theType, uint16_t theTag, uint16_t theFormat = 0)
7
+ : Type(theType), Folder(NULL) {
8
Entry.ValuePtr = NULL;
9
Entry.Tag = theTag;
10
- Entry.Format = 0;
11
+ Entry.Format = theFormat;
12
Entry.Components = 0;
13
}
14
};
15
sview-17_04.tar.gz/include/StImage/StExifTags.h -> sview-20_08.tar.gz/include/StImage/StExifTags.h
Changed
9
1
2
enum Image {
3
Image_Orientation = 0x0112,
4
Image_DateTime = 0x0132,
5
+ Image_MakerNote = 0x927C, // matches TAG_MAKER_NOTE
6
};
7
8
enum Fuji {
9
sview-17_04.tar.gz/include/StImage/StFreeImage.h -> sview-20_08.tar.gz/include/StImage/StFreeImage.h
Changed
10
1
2
ST_CPPEXPORT StFreeImage();
3
ST_CPPEXPORT virtual ~StFreeImage();
4
5
+ ST_LOCAL virtual StHandle<StImageFile> createEmpty() const ST_ATTR_OVERRIDE { return new StFreeImage(); }
6
+
7
ST_CPPEXPORT virtual void close() ST_ATTR_OVERRIDE;
8
ST_CPPEXPORT virtual bool loadExtra(const StString& theFilePath,
9
ImageType theImageType,
10
sview-17_04.tar.gz/include/StImage/StImage.h -> sview-20_08.tar.gz/include/StImage/StImage.h
Changed
29
1
2
/**
3
- * Copyright © 2010-2015 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2010-2019 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* Distributed under the Boost Software License, Version 1.0.
7
* See accompanying file license-boost.txt or copy at
8
9
ImgColor_RGBA, //!< same as RGB but has Alpha channel to perform color blending with background
10
ImgColor_GRAY, //!< just gray scale
11
ImgColor_YUV, //!< luma/brightness (Y) + chrominance (UV color plane) - widely used in cinema
12
+ ImgColor_YUVA, //!< luma/brightness (Y) + chrominance (UV color plane) + Alpha
13
ImgColor_XYZ, //!< XYZ
14
ImgColor_CMYK, //!< Cyan, Magenta, Yellow and Black - generally used in printing process
15
ImgColor_HSV, //!< Hue, Saturation, Value (also known as HSB - Hue, Saturation, Brightness)
16
17
ST_CPPEXPORT static StString formatImgColorModel(ImgColorModel theColorModel);
18
ST_LOCAL inline StString formatImgColorModel() const { return formatImgColorModel(myColorModel); }
19
20
+ /**
21
+ * Format image pixel format.
22
+ * @sa stAV::PIX_FMT::getString()
23
+ */
24
+ ST_CPPEXPORT const char* formatImgPixelFormat() const;
25
+
26
public: //! @name initializers
27
28
/**
29
sview-17_04.tar.gz/include/StImage/StImageFile.h -> sview-20_08.tar.gz/include/StImage/StImageFile.h
Changed
84
1
2
/**
3
- * Copyright © 2011-2015 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2011-2020 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* Distributed under the Boost Software License, Version 1.0.
7
* See accompanying file license-boost.txt or copy at
8
9
ST_TYPE_HDR, //!< Radiance High Dynamic Range - .hdr extension
10
ST_TYPE_WEBP,
11
ST_TYPE_WEBPLL,
12
+ ST_TYPE_DDS,
13
} ImageType;
14
15
typedef enum tagImageClass {
16
17
ST_DEVIL,
18
ST_FREEIMAGE,
19
ST_WEBP,
20
+ ST_STB,
21
} ImageClass;
22
23
public:
24
25
ST_CPPEXPORT static StHandle<StImageFile> create(ImageClass thePreferred = ST_LIBAV,
26
ImageType theImgType = ST_TYPE_NONE);
27
28
+ public:
29
+
30
/**
31
* Empty constructor.
32
*/
33
34
myMetadata = theDict;
35
}
36
37
+ /**
38
+ * Return stereoscopic format stored in the file or StFormat_AUTO if undefined.
39
+ */
40
ST_LOCAL StFormat getFormat() const {
41
return mySrcFormat;
42
}
43
44
/**
45
+ * Return panorama format stored in the file or StPanorama_OFF if undefined.
46
+ */
47
+ ST_LOCAL StPanorama getPanoramaFormat() const { return mySrcPanorama; }
48
+
49
+ /**
50
* Returns the number of frames in multi-page image.
51
*/
52
///virtual size_t getFramesCount() const = 0;
53
54
* @param theDataSize size of data in memory
55
* @return true on success
56
*/
57
- bool load(const StString& theFilePath,
58
- ImageType theImageType = ST_TYPE_NONE,
59
- uint8_t* theDataPtr = NULL, int theDataSize = 0) { return loadExtra(theFilePath, theImageType, theDataPtr, theDataSize, false); }
60
+ ST_CPPEXPORT bool load(const StString& theFilePath,
61
+ ImageType theImageType = ST_TYPE_NONE,
62
+ uint8_t* theDataPtr = NULL, int theDataSize = 0);
63
64
/**
65
* This virtual function should be implemented by inheritors.
66
67
ImageType theImageType,
68
StFormat theSrcFormat) = 0;
69
70
+ /**
71
+ * Create new instance of this class.
72
+ */
73
+ virtual StHandle<StImageFile> createEmpty() const = 0;
74
+
75
protected:
76
77
StDictionary myMetadata;
78
StString myStateDescr;
79
StFormat mySrcFormat;
80
+ StPanorama mySrcPanorama;
81
82
};
83
84
sview-17_04.tar.gz/include/StImage/StImagePlane.h -> sview-20_08.tar.gz/include/StImage/StImagePlane.h
Changed
40
1
2
/**
3
- * Copyright © 2010-2016 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2010-2020 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* Distributed under the Boost Software License, Version 1.0.
7
* See accompanying file license-boost.txt or copy at
8
9
/**
10
* This enumeration define packed image plane formats.
11
*/
12
- typedef enum tagFormat {
13
+ enum ImgFormat {
14
ImgUNKNOWN = 0, //!< not supported or unknown format
15
ImgGray = 1, //!< 1 byte per pixel (1-component plane, could be part of multiple-plane image)
16
ImgGray16, //!< 2 bytes per pixel (1-component plane)
17
18
ImgRGBAF, //!< 4 floats (16-bytes) RGBA image plane
19
ImgBGRAF, //!< same as RGBAF but with different components order
20
ImgUV, //!< 2 bytes packed UV image plane
21
- } ImgFormat;
22
+ };
23
+ enum { ImgNB = ImgUV + 1 };
24
25
ST_CPPEXPORT static StString formatImgFormat(ImgFormat theImgFormat);
26
inline StString formatImgFormat() const { return formatImgFormat(myImgFormat); }
27
28
const bool theIsCompact);
29
30
/**
31
+ * Initialize as transposed copy.
32
+ */
33
+ ST_CPPEXPORT bool initTransposedCopy(const StImagePlane& theCopy,
34
+ const bool theIsClockwise);
35
+
36
+ /**
37
* Initialize as wrapper (data will not be copied).
38
*/
39
ST_CPPEXPORT bool initWrapper(const StImagePlane& theCopy);
40
sview-17_04.tar.gz/include/StImage/StJpegParser.h -> sview-20_08.tar.gz/include/StImage/StJpegParser.h
Changed
47
1
2
ST_CPPEXPORT StString getDateTime() const;
3
4
/**
5
+ * Read 360Mono and 360Stereo EXIF property.
6
+ */
7
+ ST_CPPEXPORT bool get360PanoMakerNote(bool& theIsStereo) const;
8
+
9
+ /**
10
* Reads the parallax information from EXIF (currently - only for Fujifilm MPO).
11
* @param theParallax the parallax in per cents
12
* @return true if tag found
13
14
}
15
16
/**
17
+ * @return XMP
18
+ */
19
+ ST_LOCAL const StString& getXMP() const { return myXMP; }
20
+
21
+ /**
22
* @return stereo format stored in file
23
*/
24
ST_LOCAL StFormat getSrcFormat() const {
25
26
}
27
28
/**
29
+ * Return panorama format.
30
+ */
31
+ ST_LOCAL StPanorama getPanorama() const { return myPanorama; }
32
+
33
+ /**
34
* Parse the structure.
35
*/
36
ST_CPPEXPORT bool parse();
37
38
//!< array of offsets in image data, starting from session lenght (zero offset is invalid)
39
StString myComment; //!< string stored in COM segment (directly in JPEG, NOT inside EXIF)
40
StString myJpsComment; //!< string stored in JPS segment
41
+ StString myXMP; //!< string stored in XMP segment
42
StFormat myStFormat; //!< stereo format
43
+ StPanorama myPanorama; //!< panorama format
44
45
};
46
47
sview-20_08.tar.gz/include/StImage/StStbImage.h
Added
56
1
2
+/**
3
+ * Copyright © 2019 Kirill Gavrilov <kirill@sview.ru>
4
+ *
5
+ * Distributed under the Boost Software License, Version 1.0.
6
+ * See accompanying file license-boost.txt or copy at
7
+ * http://www.boost.org/LICENSE_1_0.txt
8
+ */
9
+
10
+#ifndef __StStbImage_h_
11
+#define __StStbImage_h_
12
+
13
+#include "StImageFile.h"
14
+
15
+// define StHandle template specialization
16
+class StStbImage;
17
+ST_DEFINE_HANDLE(StStbImage, StImageFile);
18
+
19
+/**
20
+ * This class implements image load/save operations using STB library.
21
+ */
22
+class StStbImage : public StImageFile {
23
+
24
+ public:
25
+
26
+ /**
27
+ * Should be called at application start.
28
+ */
29
+ ST_CPPEXPORT static bool init();
30
+
31
+ public:
32
+
33
+ ST_CPPEXPORT StStbImage();
34
+ ST_CPPEXPORT virtual ~StStbImage();
35
+
36
+ ST_LOCAL virtual StHandle<StImageFile> createEmpty() const ST_ATTR_OVERRIDE { return new StStbImage(); }
37
+
38
+ ST_CPPEXPORT virtual void close() ST_ATTR_OVERRIDE;
39
+ ST_CPPEXPORT virtual bool loadExtra(const StString& theFilePath,
40
+ ImageType theImageType,
41
+ uint8_t* theDataPtr,
42
+ int theDataSize,
43
+ bool theIsOnlyRGB) ST_ATTR_OVERRIDE;
44
+ ST_CPPEXPORT virtual bool save(const StString& theFilePath,
45
+ ImageType theImageType,
46
+ StFormat theSrcFormat) ST_ATTR_OVERRIDE;
47
+
48
+
49
+ private:
50
+
51
+ void* myStbImage;
52
+
53
+};
54
+
55
+#endif //__StStbImage_h_
56
sview-17_04.tar.gz/include/StImage/StWebPImage.h -> sview-20_08.tar.gz/include/StImage/StWebPImage.h
Changed
10
1
2
ST_CPPEXPORT StWebPImage();
3
ST_CPPEXPORT virtual ~StWebPImage();
4
5
+ ST_LOCAL virtual StHandle<StImageFile> createEmpty() const ST_ATTR_OVERRIDE { return new StWebPImage(); }
6
+
7
ST_CPPEXPORT virtual void close() ST_ATTR_OVERRIDE;
8
ST_CPPEXPORT virtual bool loadExtra(const StString& theFilePath,
9
ImageType theImageType,
10
sview-20_08.tar.gz/include/StJNI
Added
2
1
+(directory)
2
sview-20_08.tar.gz/include/StJNI/StJNIEnv.h
Added
68
1
2
+/**
3
+ * Copyright © 2019 Kirill Gavrilov <kirill@sview.ru>
4
+ *
5
+ * Distributed under the Boost Software License, Version 1.0.
6
+ * See accompanying file license-boost.txt or copy at
7
+ * http://www.boost.org/LICENSE_1_0.txt
8
+ */
9
+
10
+#ifndef __StJNIEnv_h__
11
+#define __StJNIEnv_h__
12
+
13
+#include <StStrings/StString.h>
14
+
15
+//#include <jni.h>
16
+
17
+struct _JNIEnv;
18
+struct _JavaVM;
19
+typedef _JNIEnv JNIEnv;
20
+typedef _JavaVM JavaVM;
21
+
22
+/**
23
+ * The sentry class for attaching the current thread to JavaVM.
24
+ */
25
+class StJNIEnv {
26
+
27
+ public:
28
+
29
+ /**
30
+ * Main constructor, tries to attach JavaVM to the current thread.
31
+ */
32
+ ST_CPPEXPORT StJNIEnv(JavaVM* theJavaVM);
33
+
34
+ /**
35
+ * Destructor, automatically detaches JavaVM from current thread.
36
+ * Has no effect if JavaVM has been attached to the thread before creating this sentry.
37
+ */
38
+ ST_CPPEXPORT ~StJNIEnv();
39
+
40
+ /**
41
+ * Detach from current thread right now.
42
+ * Has no effect if JavaVM has been attached to the thread before creating this sentry.
43
+ */
44
+ ST_CPPEXPORT void detach();
45
+
46
+ /**
47
+ * Cast to actual JNIEnv instance.
48
+ */
49
+ ST_LOCAL JNIEnv* operator->() const {
50
+ return myJniEnv;
51
+ }
52
+
53
+ /**
54
+ * Return true if JNI environment is NULL.
55
+ */
56
+ ST_LOCAL bool isNull() const { return myJniEnv == NULL; }
57
+
58
+ private:
59
+
60
+ JavaVM* myJavaVM; //!< pointer to global Java VM instance
61
+ JNIEnv* myJniEnv; //!< JNI environment for working thread
62
+ size_t myThreadId; //!< attached thread id
63
+ bool myToDetach; //!< flag to detach
64
+
65
+};
66
+
67
+#endif //__StJNIEnv_h__
68
sview-17_04.tar.gz/include/StSettings/StFloat32Param.h -> sview-20_08.tar.gz/include/StSettings/StFloat32Param.h
Changed
42
1
2
/**
3
- * Copyright © 2011-2016 Kirill Gavrilov
4
+ * Copyright © 2011-2017 Kirill Gavrilov
5
*
6
* Distributed under the Boost Software License, Version 1.0.
7
* See accompanying file license-boost.txt or copy at
8
9
}
10
11
/**
12
+ * @return parameter format
13
+ */
14
+ ST_LOCAL const StString& getFormat() const {
15
+ return myParamFormat;
16
+ }
17
+
18
+ /**
19
+ * Set new parameter format.
20
+ */
21
+ ST_LOCAL void setFormat(const StString& theFormat) {
22
+ myParamFormat = theFormat;
23
+ }
24
+
25
+ /**
26
* Return true if parameter defines minimum value limit.
27
*/
28
ST_LOCAL bool hasMinValue() const {
29
30
31
StString myParamKey; //!< parameter key (id)
32
StString myParamName; //!< parameter name (label)
33
+ StString myParamFormat; //!< parameter format
34
35
};
36
37
+// define StHandle template specialization
38
+ST_DEFINE_HANDLE(StParam<float>, StParamBase);
39
+ST_DEFINE_HANDLE(StFloat32Param, StParam<float>);
40
+
41
#endif // __StFloat32Param_h_
42
sview-17_04.tar.gz/include/StSlots/StAction.h -> sview-20_08.tar.gz/include/StSlots/StAction.h
Changed
128
1
2
/**
3
- * Copyright © 2013 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2013-2017 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* Distributed under the Boost Software License, Version 1.0.
7
* See accompanying file license-boost.txt or copy at
8
9
virtual void doTrigger(const StEvent* theEvent) = 0;
10
11
/**
12
- * @return hot key 1 to trigger action
13
+ * @return hot key to trigger action
14
*/
15
- ST_LOCAL unsigned int getHotKey1() const {
16
- return myHotKey1;
17
+ ST_LOCAL unsigned int getHotKey(int theIndex) const {
18
+ ST_DEBUG_ASSERT(theIndex >= 0 && theIndex <= 1)
19
+ return myHotKeys[theIndex];
20
}
21
22
/**
23
* @return hot key 1 to trigger action
24
*/
25
- ST_LOCAL unsigned int& changeHotKey1() {
26
- return myHotKey1;
27
+ ST_LOCAL unsigned int getHotKey1() const { return myHotKeys[0]; }
28
+
29
+ /**
30
+ * @return hot key 1 to trigger action
31
+ */
32
+ ST_LOCAL unsigned int& changeHotKey1() { return myHotKeys[0]; }
33
+
34
+ /**
35
+ * @param theKey hot key to trigger action
36
+ */
37
+ ST_LOCAL void setHotKey(int theIndex, unsigned int theKey) {
38
+ ST_DEBUG_ASSERT(theIndex >= 0 && theIndex <= 1)
39
+ myHotKeys[theIndex] = theKey;
40
}
41
42
/**
43
* @param theKey hot key 1 to trigger action
44
*/
45
- ST_LOCAL void setHotKey1(unsigned int theKey) {
46
- myHotKey1 = theKey;
47
- }
48
+ ST_LOCAL void setHotKey1(unsigned int theKey) { myHotKeys[0] = theKey; }
49
50
/**
51
* Default value of hot key 1.
52
*/
53
- ST_LOCAL unsigned int getDefaultHotKey1() const {
54
- return myDefaultHotKey1;
55
- }
56
+ ST_LOCAL unsigned int getDefaultHotKey1() const { return myHotKeysDef[0]; }
57
58
/**
59
* @param theKey default value of hot key 1
60
*/
61
ST_LOCAL void setDefaultHotKey1(unsigned int theKey) {
62
- myDefaultHotKey1 = theKey;
63
- myHotKey1 = theKey;
64
+ myHotKeysDef[0] = theKey;
65
+ myHotKeys[0] = theKey;
66
}
67
68
/**
69
* @return hot key 2 to trigger action
70
*/
71
- ST_LOCAL unsigned int getHotKey2() const {
72
- return myHotKey2;
73
- }
74
+ ST_LOCAL unsigned int getHotKey2() const { return myHotKeys[1]; }
75
76
/**
77
* @return hot key 2 to trigger action
78
*/
79
- ST_LOCAL unsigned int& changeHotKey2() {
80
- return myHotKey2;
81
- }
82
+ ST_LOCAL unsigned int& changeHotKey2() { return myHotKeys[1]; }
83
84
/**
85
* @param theKey hot key 2 to trigger action
86
*/
87
- ST_LOCAL void setHotKey2(unsigned int theKey) {
88
- myHotKey2 = theKey;
89
- }
90
+ ST_LOCAL void setHotKey2(unsigned int theKey) { myHotKeys[1] = theKey; }
91
92
/**
93
* Default value of hot key 2.
94
*/
95
- ST_LOCAL unsigned int getDefaultHotKey2() const {
96
- return myDefaultHotKey2;
97
- }
98
+ ST_LOCAL unsigned int getDefaultHotKey2() const { return myHotKeysDef[1]; }
99
100
/**
101
* @param theKey default value of hot key 2
102
*/
103
ST_LOCAL void setDefaultHotKey2(unsigned int theKey) {
104
- myDefaultHotKey2 = theKey;
105
- myHotKey2 = theKey;
106
+ myHotKeysDef[1] = theKey;
107
+ myHotKeys[1] = theKey;
108
}
109
110
/**
111
112
113
protected:
114
115
- StString myName; //!< action name
116
- unsigned int myHotKey1; //!< key combination to execute action
117
- unsigned int myHotKey2; //!< key combination to execute action (extra)
118
- unsigned int myDefaultHotKey1; //!< default value of hot-key1
119
- unsigned int myDefaultHotKey2; //!< default value of hot-key2
120
- bool myToHoldKey; //!< this action process key hold event
121
+ StString myName; //!< action name
122
+ unsigned int myHotKeys[2]; //!< key combination to execute action
123
+ unsigned int myHotKeysDef[2]; //!< default value of hot-key1
124
+ bool myToHoldKey; //!< this action process key hold event
125
126
};
127
128
sview-17_04.tar.gz/include/StStrings/StStringStream.h -> sview-20_08.tar.gz/include/StStrings/StStringStream.h
Changed
17
1
2
/**
3
- * Copyright © 2011-2014 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2011-2017 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* Distributed under the Boost Software License, Version 1.0.
7
* See accompanying file license-boost.txt or copy at
8
9
#if defined(_WIN32)
10
#define ST_NO_XLOCALE
11
#warning xlocale is not supported by compiler!
12
- #else
13
+ #elif !defined(__GLIBC__)
14
#include <xlocale.h>
15
#endif
16
#endif
17
sview-17_04.tar.gz/include/StStrings/StStringUnicode.h -> sview-20_08.tar.gz/include/StStrings/StStringUnicode.h
Changed
13
1
2
StStringUnicode unquoted() const;
3
4
/**
5
+ * Cut off all leading space characters.
6
+ */
7
+ void leftAdjust();
8
+
9
+ /**
10
* Cut off all trailing space characters.
11
*/
12
void rightAdjust();
13
sview-17_04.tar.gz/include/StStrings/StStringUnicode.inl -> sview-20_08.tar.gz/include/StStrings/StStringUnicode.inl
Changed
104
1
2
this->Size = 0;
3
this->Length = 0;
4
char aBuff[32];
5
-#if defined(_MSC_VER)
6
- stsprintf(aBuff, 32, "%I64i", theInt64);
7
-#elif (defined(_WIN64) || defined(__WIN64__)\
8
- || defined(_LP64) || defined(__LP64__))
9
- stsprintf(aBuff, 32, "%li", theInt64);
10
-#else
11
- stsprintf(aBuff, 32, "%lli", theInt64);
12
-#endif
13
+ stsprintf(aBuff, 32, "%" PRId64, theInt64);
14
fromUnicode(aBuff);
15
}
16
17
18
this->Size = 0;
19
this->Length = 0;
20
char aBuff[32];
21
-#if defined(_MSC_VER)
22
- stsprintf(aBuff, 32, "%I64u", theUInt64);
23
-#elif (defined(_WIN64) || defined(__WIN64__)\
24
- || defined(_LP64) || defined(__LP64__))
25
- stsprintf(aBuff, 32, "%lu", theUInt64);
26
-#else
27
- stsprintf(aBuff, 32, "%llu", theUInt64);
28
-#endif
29
+ stsprintf(aBuff, 32, "%" PRIu64, theUInt64);
30
fromUnicode(aBuff);
31
}
32
33
34
this->Size = 0;
35
this->Length = 0;
36
char aBuff[32];
37
-#if defined(_MSC_VER)
38
- stsprintf(aBuff, 32, "%I64i", theInt64);
39
-#elif (defined(_WIN64) || defined(__WIN64__)\
40
- || defined(_LP64) || defined(__LP64__))
41
- stsprintf(aBuff, 32, "%li", theInt64);
42
-#else
43
- stsprintf(aBuff, 32, "%lli", theInt64);
44
-#endif
45
+ stsprintf(aBuff, 32, "%" PRId64, (int64_t )theInt64);
46
fromUnicode(aBuff);
47
}
48
49
50
this->Size = 0;
51
this->Length = 0;
52
char aBuff[32];
53
-#if defined(_MSC_VER)
54
- stsprintf(aBuff, 32, "%I64u", theUInt64);
55
-#elif (defined(_WIN64) || defined(__WIN64__)\
56
- || defined(_LP64) || defined(__LP64__))
57
- stsprintf(aBuff, 32, "%lu", theUInt64);
58
-#else
59
- stsprintf(aBuff, 32, "%llu", theUInt64);
60
-#endif
61
+ stsprintf(aBuff, 32, "%" PRIu64, (uint64_t )theUInt64);
62
fromUnicode(aBuff);
63
}
64
#endif
65
66
template<typename Type> inline
67
StStringUnicode<Type> StStringUnicode<Type>::replace(const StStringUnicode<Type>& theSubString,
68
const StStringUnicode<Type>& theReplacer) const {
69
- if(theSubString.isEmpty() || this->isEmpty() || theSubString.Size >= this->Size) {
70
+ if(theSubString.isEmpty() || this->isEmpty() || theSubString.Size > this->Size) {
71
// just make a copy
72
return *this;
73
+ } else if(theSubString.Size == this->Size) {
74
+ if(theSubString.isEquals(*this)) {
75
+ return theReplacer;
76
+ }
77
}
78
StUtfIterator<Type> anIter(this->String);
79
StStringUnicode<Type> aResult;
80
81
}
82
83
template<typename Type> inline
84
+void StStringUnicode<Type>::leftAdjust() {
85
+ if(this->Length == 0) {
86
+ return;
87
+ }
88
+ for(size_t anIter = 0; anIter < this->Size / sizeof(Type); ++anIter) {
89
+ if(this->String[anIter] != (Type )' '
90
+ && this->String[anIter] != (Type )'\t') {
91
+ if(anIter != 0) {
92
+ StStringUnicode<Type> aCopy(&this->String[anIter]);
93
+ *this = aCopy;
94
+ }
95
+ return;
96
+ }
97
+ }
98
+}
99
+
100
+template<typename Type> inline
101
void StStringUnicode<Type>::rightAdjust() {
102
if(this->Length == 0) {
103
return;
104
sview-17_04.tar.gz/include/StStrings/StUtfIterator.h -> sview-20_08.tar.gz/include/StStrings/StUtfIterator.h
Changed
10
1
2
inline const Type* getBufferNext() const { return myPosNext; }
3
4
/**
5
- * Return the index displacement from iterator intialization.
6
+ * Return the index displacement from iterator initialization.
7
*/
8
inline size_t getIndex() const {
9
return myCharIndex;
10
sview-17_04.tar.gz/include/StTemplates/StRect.h -> sview-20_08.tar.gz/include/StTemplates/StRect.h
Changed
9
1
2
3
typedef StRect<int> StRectI_t;
4
typedef StRect<double> StRectD_t;
5
+typedef StRect<float> StRectF_t;
6
7
/**
8
* Simple structure to define rectangular margins.
9
sview-17_04.tar.gz/include/StTemplates/StTemplates.h -> sview-20_08.tar.gz/include/StTemplates/StTemplates.h
Changed
15
1
2
return (TypePtr )::stMemAllocZeroAligned(bytesCount, align);
3
}
4
5
-template<typename TypePtr>
6
-inline TypePtr stMemReallocAligned(TypePtr ptrAligned,
7
- const size_t& bytesCount,
8
- const size_t& align = ST_ALIGNMENT) {
9
- return (TypePtr )::stMemReallocAligned(ptrAligned, bytesCount, align);
10
-}
11
-
12
/**
13
* Auxiliary functions.
14
*/
15
sview-17_04.tar.gz/include/StTemplates/StVec2.h -> sview-20_08.tar.gz/include/StTemplates/StVec2.h
Changed
45
1
2
v[1] / theInvFactor);
3
}
4
5
+ /**
6
+ * Return component-wise minimum of two vectors.
7
+ */
8
+ StVec2 cwiseMin(const StVec2& theVec) const {
9
+ return StVec2(v[0] < theVec.v[0] ? v[0] : theVec.v[0],
10
+ v[1] < theVec.v[1] ? v[1] : theVec.v[1]);
11
+ }
12
+
13
+ /**
14
+ * Return component-wise maximum of two vectors.
15
+ */
16
+ StVec2 cwiseMax(const StVec2& theVec) const {
17
+ return StVec2(v[0] > theVec.v[0] ? v[0] : theVec.v[0],
18
+ v[1] > theVec.v[1] ? v[1] : theVec.v[1]);
19
+ }
20
+
21
+ /**
22
+ * Compute component-wise modulus of the vector.
23
+ */
24
+ StVec2 cwiseAbs() const {
25
+ return StVec2(std::abs(v[0]), std::abs(v[1]));
26
+ }
27
+
28
+ /**
29
+ * Compute maximum component of the vector.
30
+ */
31
+ Element_t maxComp() const {
32
+ return v[0] > v[1] ? v[0] : v[1];
33
+ }
34
+
35
+ /**
36
+ * Compute minimum component of the vector.
37
+ */
38
+ Element_t minComp() const {
39
+ return v[0] < v[1] ? v[0] : v[1];
40
+ }
41
+
42
};
43
44
// help structures
45
sview-17_04.tar.gz/include/StTemplates/StVec3.h -> sview-20_08.tar.gz/include/StTemplates/StVec3.h
Changed
49
1
2
}
3
4
/**
5
+ * Return component-wise minimum of two vectors.
6
+ */
7
+ StVec3 cwiseMin(const StVec3& theVec) const {
8
+ return StVec3(v[0] < theVec.v[0] ? v[0] : theVec.v[0],
9
+ v[1] < theVec.v[1] ? v[1] : theVec.v[1],
10
+ v[2] < theVec.v[2] ? v[2] : theVec.v[2]);
11
+ }
12
+
13
+ /**
14
+ * Return component-wise maximum of two vectors.
15
+ */
16
+ StVec3 cwiseMax(const StVec3& theVec) const {
17
+ return StVec3(v[0] > theVec.v[0] ? v[0] : theVec.v[0],
18
+ v[1] > theVec.v[1] ? v[1] : theVec.v[1],
19
+ v[2] > theVec.v[2] ? v[2] : theVec.v[2]);
20
+ }
21
+
22
+ /**
23
+ * Return component-wise modulus of the vector.
24
+ */
25
+ StVec3 cwiseAbs() const {
26
+ return StVec3(std::abs (v[0]), std::abs (v[1]), std::abs (v[2]));
27
+ }
28
+
29
+ /**
30
+ * Return maximum component of the vector.
31
+ */
32
+ Element_t maxComp() const {
33
+ return v[0] > v[1] ? (v[0] > v[2] ? v[0] : v[2])
34
+ : (v[1] > v[2] ? v[1] : v[2]);
35
+ }
36
+
37
+ /**
38
+ * Return minimum component of the vector.
39
+ */
40
+ Element_t minComp() const {
41
+ return v[0] < v[1] ? (v[0] < v[2] ? v[0] : v[2])
42
+ : (v[1] < v[2] ? v[1] : v[2]);
43
+ }
44
+
45
+ /**
46
* Compute linear interpolation between to vectors.
47
* @param theT (const Element_t ) - interpolation coefficient 0..1;
48
* @return interpolation result.
49
sview-17_04.tar.gz/include/StTemplates/StVec4.h -> sview-20_08.tar.gz/include/StTemplates/StVec4.h
Changed
53
1
2
return StString('(') + x() + "; " + y() + "; " + z() + "; " + w() + ')';
3
}
4
5
+ /**
6
+ * Return component-wise minimum of two vectors.
7
+ */
8
+ StVec4 cwiseMin(const StVec4& theVec) const {
9
+ return StVec4(v[0] < theVec.v[0] ? v[0] : theVec.v[0],
10
+ v[1] < theVec.v[1] ? v[1] : theVec.v[1],
11
+ v[2] < theVec.v[2] ? v[2] : theVec.v[2],
12
+ v[3] < theVec.v[3] ? v[3] : theVec.v[3]);
13
+ }
14
+
15
+ /**
16
+ * Return component-wise maximum of two vectors.
17
+ */
18
+ StVec4 cwiseMax(const StVec4& theVec) const {
19
+ return StVec4(v[0] > theVec.v[0] ? v[0] : theVec.v[0],
20
+ v[1] > theVec.v[1] ? v[1] : theVec.v[1],
21
+ v[2] > theVec.v[2] ? v[2] : theVec.v[2],
22
+ v[3] > theVec.v[3] ? v[3] : theVec.v[3]);
23
+ }
24
+
25
+ /**
26
+ * Return component-wise modulus of the vector.
27
+ */
28
+ StVec4 cwiseAbs() const {
29
+ return StVec4(std::abs (v[0]), std::abs (v[1]), std::abs (v[2]), std::abs (v[3]));
30
+ }
31
+
32
+ /**
33
+ * Return maximum component of the vector.
34
+ */
35
+ Element_t maxComp() const {
36
+ const Element_t aMax1 = v[0] > v[1] ? v[0] : v[1];
37
+ const Element_t aMax2 = v[2] > v[3] ? v[2] : v[3];
38
+ return aMax1 > aMax2 ? aMax1 : aMax2;
39
+ }
40
+
41
+ /**
42
+ * Return minimum component of the vector.
43
+ */
44
+ Element_t minComp() const {
45
+ const Element_t aMin1 = v[0] < v[1] ? v[0] : v[1];
46
+ const Element_t aMin2 = v[2] < v[3] ? v[2] : v[3];
47
+ return aMin1 < aMin2 ? aMin1 : aMin2;
48
+ }
49
+
50
};
51
52
/**
53
sview-17_04.tar.gz/include/StThreads/StResourceManager.h -> sview-20_08.tar.gz/include/StThreads/StResourceManager.h
Changed
9
1
2
*/
3
enum FolderId {
4
FolderId_SdCard,
5
+ FolderId_Documents,
6
FolderId_Downloads,
7
FolderId_Pictures,
8
FolderId_Photos,
9
sview-17_04.tar.gz/include/StThreads/StThread.h -> sview-20_08.tar.gz/include/StThreads/StThread.h
Changed
10
1
2
/**
3
* This is a header for threads creating/manipulating.
4
* (redefinition for WinAPI and POSIX threads)
5
- * Copyright © 2008-2013 Kirill Gavrilov <kirill@sview.ru>
6
+ * Copyright © 2008-2017 Kirill Gavrilov <kirill@sview.ru>
7
*
8
* Distributed under the Boost Software License, Version 1.0.
9
* See accompanying file license-boost.txt or copy at
10
sview-17_04.tar.gz/include/StThreads/StTimer.h -> sview-20_08.tar.gz/include/StThreads/StTimer.h
Changed
34
1
2
* Just start the timer again.
3
*/
4
void resume() {
5
- stMemSet(&myCounterStart, 0, sizeof(myCounterStart));
6
- myIsPaused = false;
7
-
8
- fillCounter(myCounterStart);
9
+ if(myIsPaused) {
10
+ stMemSet(&myCounterStart, 0, sizeof(myCounterStart));
11
+ myIsPaused = false;
12
+ fillCounter(myCounterStart);
13
+ }
14
}
15
16
/**
17
18
* Pause the timer (freeze current timestamp).
19
*/
20
void pause() {
21
- // increment our timer value
22
- myTimeInMicroSec += getElapsedTimeFromLastStartInMicroSec();
23
- // set timer paused flag
24
- myIsPaused = true;
25
+ if(!myIsPaused) {
26
+ // increment our timer value
27
+ myTimeInMicroSec += getElapsedTimeFromLastStartInMicroSec();
28
+ // set timer paused flag
29
+ myIsPaused = true;
30
+ }
31
}
32
33
/**
34
sview-17_04.tar.gz/include/stTypes.h -> sview-20_08.tar.gz/include/stTypes.h
Changed
129
1
2
/**
3
- * Copyright © 2009-2014 Kirill Gavrilov <kirill@sview.ru>
4
+ * Copyright © 2009-2017 Kirill Gavrilov <kirill@sview.ru>
5
*
6
* Distributed under the Boost Software License, Version 1.0.
7
* See accompanying file license-boost.txt or copy at
8
9
#define ST_ATTR_DEPRECATED
10
#endif
11
12
+// Disable deprecation warnings.
13
+#if defined(__ICL) || defined (__INTEL_COMPILER)
14
+ #define ST_DISABLE_DEPRECATION_WARNINGS __pragma(warning(push)) __pragma(warning(disable:1478))
15
+ #define ST_ENABLE_DEPRECATION_WARNINGS __pragma(warning(pop))
16
+#elif defined(_MSC_VER)
17
+ #define ST_DISABLE_DEPRECATION_WARNINGS __pragma(warning(push)) __pragma(warning(disable:4996))
18
+ #define ST_ENABLE_DEPRECATION_WARNINGS __pragma(warning(pop))
19
+#elif (defined(__GNUC__) && __GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 6)) || defined(__clang__)
20
+ // available since at least gcc 4.2 (maybe earlier), however only gcc 4.6+ supports this pragma inside the function body
21
+ // CLang also supports this gcc syntax (in addition to "clang diagnostic ignored")
22
+ #define ST_DISABLE_DEPRECATION_WARNINGS _Pragma("GCC diagnostic ignored \"-Wdeprecated-declarations\"")
23
+ #define ST_ENABLE_DEPRECATION_WARNINGS _Pragma("GCC diagnostic warning \"-Wdeprecated-declarations\"")
24
+#else
25
+ #define ST_DISABLE_DEPRECATION_WARNINGS
26
+ #define ST_ENABLE_DEPRECATION_WARNINGS
27
+#endif
28
+
29
#if defined(__cplusplus) && (__cplusplus >= 201100L)
30
- // part of C++11 standard
31
- #define ST_ATTR_OVERRIDE override
32
+ // part of C++11 standard
33
+ #define ST_ATTR_OVERRIDE override
34
#elif defined(_MSC_VER) && (_MSC_VER >= 1700)
35
- // versions before VS2012 emits warning as MSVC-specific extension
36
- #define ST_ATTR_OVERRIDE override
37
+ // versions before VS2012 emits warning as MSVC-specific extension
38
+ #define ST_ATTR_OVERRIDE override
39
#else
40
- #define ST_ATTR_OVERRIDE
41
+ #define ST_ATTR_OVERRIDE
42
#endif
43
44
#if defined(_MSC_VER)
45
46
#include <cstddef> // size_t, NULL
47
#include <cstdlib>
48
#include <cstring> // for memcpy
49
+
50
+#if(defined(_MSC_VER) && (_MSC_VER < 1800))
51
+ // only Visual Studio 2013+ (vc12) provides <cinttypes> header
52
+ #define PRId64 "I64d"
53
+ #define PRIu64 "I64u"
54
+ #define SCNd64 "I64d"
55
+ #define SCNu64 "I64u"
56
+ #ifdef _WIN64
57
+ #define PRIdPTR "I64d"
58
+ #define PRIuPTR "I64u"
59
+ #define SCNdPTR "I64d"
60
+ #define SCNuPTR "I64u"
61
+ #else
62
+ #define PRIdPTR "d"
63
+ #define PRIuPTR "u"
64
+ #define SCNdPTR "d"
65
+ #define SCNuPTR "u"
66
+ #endif
67
+#else
68
+ // use <inttypes.h< (C99) instead of <cinttypes> (C++11) for compatibility
69
+ #ifndef __STDC_FORMAT_MACROS
70
+ #define __STDC_FORMAT_MACROS
71
+ #endif
72
+ #include <inttypes.h>
73
+#endif
74
+
75
#if defined(__i386) || defined(__x86_64) || defined(_M_IX86) || defined(_M_X64) || defined(_M_AMD64)
76
#include <xmmintrin.h> // for memory alignment
77
#endif
78
79
const size_t& theAlign = ST_ALIGNMENT) {
80
#if defined(_MSC_VER)
81
return _aligned_malloc(theNbBytes, theAlign);
82
-#elif defined(__ANDROID__)
83
+#elif defined(__ANDROID__) || defined(__QNX__)
84
return memalign(theAlign, theNbBytes);
85
-#else
86
+#elif (defined(__GNUC__) && __GNUC__ >= 4 && __GNUC_MINOR__ >= 1 && (defined(__i386) || defined(__x86_64)))
87
return _mm_malloc(theNbBytes, theAlign);
88
+#else
89
+ void* aPtr;
90
+ if(posix_memalign(&aPtr, theAlign, theNbBytes)) {
91
+ return NULL;
92
+ }
93
+ return aPtr;
94
#endif
95
}
96
97
98
return aPtr;
99
}
100
101
-inline void* stMemReallocAligned(void* thePtrAligned, const size_t& theNbBytes,
102
- const size_t& theAlign = ST_ALIGNMENT) {
103
-#if defined(_MSC_VER)
104
- return _aligned_realloc(thePtrAligned, theNbBytes, theAlign);
105
-#else
106
- /// TODO (Kirill Gavrilov#4) what should we call here???
107
- return realloc(thePtrAligned, theNbBytes);
108
-#endif
109
-}
110
-
111
/**
112
* Deallocate space in memory.
113
* @param ptr (void* ) - pointer to a memory block previously allocated with stMemAllocAligned() to be deallocated.
114
115
inline void stMemFreeAligned(void* thePtrAligned) {
116
#if defined(_MSC_VER)
117
_aligned_free(thePtrAligned);
118
-#elif defined(__ANDROID__)
119
+#elif defined(__ANDROID__) || defined(__QNX__)
120
free(thePtrAligned);
121
-#else
122
+#elif (defined(__GNUC__) && __GNUC__ >= 4 && __GNUC_MINOR__ >= 1 && (defined(__i386) || defined(__x86_64)))
123
_mm_free(thePtrAligned);
124
+#else
125
+ free(thePtrAligned);
126
#endif
127
}
128
129
sview-17_04.tar.gz/include/stconfig.conf -> sview-20_08.tar.gz/include/stconfig.conf
Changed
22
1
2
#define ST_DEBUG_LOG_TO_FILE "sView.log"
3
#endif
4
5
+// notify about updates available on sview.ru
6
+#define ST_UPDATES_CHECK
7
+
8
// This is TimeBomb flag
9
// must be unset for release
10
#ifndef ST_TIMEBOMB
11
12
// Web UI using lightweight server mongoose
13
#define ST_HAVE_MONGOOSE
14
15
-//#define ST_HAVE_LIBOVR
16
+// enable OpenVR on Windows by default
17
+#ifdef _WIN32
18
+ #define ST_HAVE_OPENVR
19
+#endif
20
21
#endif //__stConfig_conf_
22
sview-17_04.tar.gz/sview/AndroidManifest.xml -> sview-20_08.tar.gz/sview/AndroidManifest.xml
Changed
49
1
2
<?xml version="1.0" encoding="utf-8"?>
3
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
4
package="com.sview"
5
- android:versionCode="16"
6
- android:versionName="16.12"
7
+ android:versionCode="44"
8
+ android:versionName="20.01"
9
android:installLocation="auto">
10
<application android:label="@string/app_name"
11
android:hasCode="true"
12
android:icon="@drawable/ic_launcher">
13
<uses-library android:name="com.s3dv.s3dvsurface" android:required="false" />
14
+
15
+ <!-- Movie Player foreground service for background audio playback -->
16
+ <service android:name="com.sview.StMovieService"
17
+ android:exported="false"
18
+ android:description="@string/app_movie_service_desc" />
19
+
20
<!-- Movie Player -->
21
<activity android:name="com.sview.StMovieActivity"
22
android:label="@string/app_movie_name"
23
android:launchMode="singleTask"
24
android:alwaysRetainTaskState="true"
25
+ android:resizeableActivity="true"
26
android:configChanges="orientation|keyboardHidden|screenSize"
27
android:theme="@android:style/Theme.NoTitleBar.Fullscreen">
28
<!-- android:documentLaunchMode="always" - available since Android 5.0 -->
29
30
<activity android:name="com.sview.StImageActivity"
31
android:label="@string/app_image_name"
32
android:launchMode="singleTask"
33
+ android:resizeableActivity="true"
34
android:configChanges="orientation|keyboardHidden|screenSize"
35
android:theme="@android:style/Theme.NoTitleBar.Fullscreen">
36
<!-- android:documentLaunchMode="always" - available since Android 5.0 -->
37
38
<activity android:name="com.sview.CrashReportActivity" android:label="@string/app_crash_name" android:configChanges="orientation|keyboardHidden"><intent-filter><action android:name="android.intent.action.MAIN" /><category android:name="android.intent.category.DEFAULT" /></intent-filter></activity>
39
</application>
40
41
- <uses-sdk android:minSdkVersion="15" />
42
+ <uses-sdk android:minSdkVersion="15" android:targetSdkVersion="28" />
43
<uses-feature android:glEsVersion="0x00020000"/>
44
<uses-permission android:name="android.permission.INTERNET" />
45
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
46
+ <uses-permission android:name="android.permission.WAKE_LOCK" />
47
+ <uses-permission android:name="android.permission.FOREGROUND_SERVICE" />
48
</manifest>
49
sview-17_04.tar.gz/sview/Contents/Info.plist -> sview-20_08.tar.gz/sview/Contents/Info.plist
Changed
19
1
2
<key>CFBundleExecutable</key>
3
<string>sView</string>
4
<key>CFBundleGetInfoString</key>
5
- <string>Copyright © Kirill Gavrilov, 2007-2017</string>
6
+ <string>Copyright © Kirill Gavrilov, 2007-2020</string>
7
<key>CFBundleIdentifier</key>
8
<string>com.sView</string>
9
<key>CFBundleInfoDictionaryVersion</key>
10
11
<key>DTXcodeBuild</key>
12
<string>10M2518</string>
13
<key>LSMinimumSystemVersion</key>
14
- <string>10.6</string>
15
+ <string>10.10</string>
16
<key>NSMainNibFile</key>
17
<string>MainMenu</string>
18
<key>NSPrincipalClass</key>
19
sview-17_04.tar.gz/sview/Resources/English.lproj/MainMenu.xib -> sview-20_08.tar.gz/sview/Resources/English.lproj/MainMenu.xib
Changed
10
1
2
<object class="NSTextFieldCell" key="NSCell" id="955175397">
3
<int key="NSCellFlags">70385217</int>
4
<int key="NSCellFlags2">138544128</int>
5
- <string key="NSContents">Copyright © Kirill Gavrilov, 2007-2017•www.sview.ru</string>
6
+ <string key="NSContents">Copyright © Kirill Gavrilov, 2007-2020•www.sview.ru</string>
7
<object class="NSFont" key="NSSupport" id="26">
8
<string key="NSName">LucidaGrande</string>
9
<double key="NSSize">11</double>
10
sview-17_04.tar.gz/sview/StMultiApp.cpp -> sview-20_08.tar.gz/sview/StMultiApp.cpp
Changed
46
1
2
static StString getAbout() {
3
StString anAboutString =
4
StString("sView ") + StVersionInfo::getSDKVersionString() + '\n'
5
- + "Copyright (C) 2007-2016 Kirill Gavrilov (kirill@sview.ru).\n"
6
+ + "Copyright (C) 2007-2020 Kirill Gavrilov (kirill@sview.ru).\n"
7
+ "Usage: sView [options] - file\n"
8
+ "Available options:\n"
9
" --fullscreen Open fullscreen\n"
10
11
" --slideshow Start slideshow\n"
12
" --last Open last file\n"
13
" --paused Open file in paused state\n"
14
+ " --seek=SECONDS Seek to specified position\n"
15
" --in=image,video Application to open (predefined values: image, video, diag)\n"
16
" --out=RENDERER Stereoscopic output module (auto, StOutAnaglyph, StOutDual,...)\n"
17
" --imageLib=IMGLIB Setup 3rd-party library for image processing (FFmpeg, FreeImage, DevIL)\n"
18
19
" mute - mute/unmute audio\n"
20
" vol?VOLUME - specify volume in percents\n"
21
" prev,next - play previous/next item in playlist\n"
22
+ " seek?SECONDS - specify volume in percents\n"
23
" fastbwd,fastfwd - seek backward/forward\n"
24
" quit - close the program\n"
25
" current?title - print title of currently played item\n"
26
27
} else if(anActLow == "currenttitle") {
28
anAction = "current?title";
29
} else if(anAction.isContains('?')) {
30
- anAction = anAction;
31
+ //anAction = anAction;
32
} else if(anActLow == "fastbwd") {
33
anAction = "action?DoSeekLeft";
34
} else if(anActLow == "fastfwd") {
35
36
// select application
37
const StString ARGUMENT_DRAWER = "in";
38
StArgument anArgDrawer = anArgs[ARGUMENT_DRAWER];
39
+ if(!anInfo->hasPath() && !anArgDrawer.isValid()) {
40
+ StApplication::readDefaultDrawer(anInfo);
41
+ anArgDrawer = anInfo->getArgumentsMap()[ARGUMENT_DRAWER];
42
+ }
43
if(anArgDrawer.isValid()) {
44
if(anArgDrawer.getValue() == "image"
45
|| anArgDrawer.getValue() == "StImageViewer") {
46
sview-17_04.tar.gz/sview/main.ObjC.mm -> sview-20_08.tar.gz/sview/main.ObjC.mm
Changed
34
1
2
}
3
}
4
}
5
- if(TheOpenInfo->hasPath()
6
- || anArgsNb > 1) {
7
- // create StApplication instance only if we know which drawer plugin to launch
8
+
9
+ // create StApplication instance only if we know which drawer plugin to launch
10
+ bool toStart = true;
11
+ //bool toStart = TheOpenInfo->hasPath() || anArgsNb > 1;
12
+ //if(!toStart) { toStart = StApplication::readDefaultDrawer(TheOpenInfo); }
13
+ if(toStart) {
14
[self launchSelf: NULL];
15
}
16
myIsStarted = true;
17
18
}
19
20
if(myStApp->closingDown()) {
21
+ StHandle<StOpenInfo> anOther = myStApp->getOpenFileInOtherDrawer();
22
+ if(!anOther.isNull()) {
23
+ myStApp.nullify();
24
+ StHandle<StResourceManager> aResMgr = new StResourceManager();
25
+ myStApp = StMultiApp::getInstance(aResMgr, anOther);
26
+ if(!myStApp.isNull() && myStApp->open()) {
27
+ return true;
28
+ }
29
+ }
30
+
31
myStApp.nullify();
32
33
// this will call exit(), so code below has no effect
34
sview-17_04.tar.gz/sview/main.cpp -> sview-20_08.tar.gz/sview/main.cpp
Changed
25
1
2
3
StHandle<StResourceManager> aResMgr = new StResourceManager();
4
StHandle<StApplication> anApp = StMultiApp::getInstance(aResMgr);
5
- if(anApp.isNull() || !anApp->open()) {
6
- return 1;
7
+ for(;;) {
8
+ if(anApp.isNull() || !anApp->open()) {
9
+ return 1;
10
+ }
11
+
12
+ int aResult = anApp->exec();
13
+ StHandle<StOpenInfo> anOther = anApp->getOpenFileInOtherDrawer();
14
+ if(anOther.isNull()) {
15
+ return aResult;
16
+ }
17
+
18
+ anApp.nullify();
19
+ anApp = StMultiApp::getInstance(aResMgr, anOther);
20
}
21
- return anApp->exec();
22
}
23
24
#endif // __APPLE__
25
sview-20_08.tar.gz/sview/res/drawable-hdpi/ic_media_play.png
Added
sview-20_08.tar.gz/sview/res/drawable-mdpi/ic_media_play.png
Added
sview-20_08.tar.gz/sview/res/drawable-xhdpi/ic_media_play.png
Added
sview-20_08.tar.gz/sview/res/drawable-xxhdpi/ic_media_play.png
Added
sview-17_04.tar.gz/sview/res/values/strings.xml -> sview-20_08.tar.gz/sview/res/values/strings.xml
Changed
7
1
2
<string name="app_image_name">sView - Image Viewer</string>
3
<string name="app_movie_name">sView - Media Player</string>
4
<string name="app_crash_name">sView - Crash Report</string>
5
+ <string name="app_movie_service_desc">sView - service playing audio in background</string>
6
</resources>
7
sview-17_04.tar.gz/sview/src/com/sview/StActivity.java -> sview-20_08.tar.gz/sview/src/com/sview/StActivity.java
Changed
220
1
2
myContext = new ContextWrapper(this);
3
myContext.getExternalFilesDir(null);
4
5
+ askUserPermission(android.Manifest.permission.WRITE_EXTERNAL_STORAGE, null);
6
+
7
+ android.os.PowerManager aPowerManager = (android.os.PowerManager)getSystemService(Context.POWER_SERVICE);
8
+ myWakeLock = aPowerManager.newWakeLock(android.os.PowerManager.PARTIAL_WAKE_LOCK, "sView.PartialWakeLock");
9
+
10
mySensorMgr = (SensorManager )getSystemService(Context.SENSOR_SERVICE);
11
mySensorOri = mySensorMgr.getDefaultSensor(Sensor.TYPE_ROTATION_VECTOR);
12
if(mySensorOri == null) {
13
14
anInfo.append("Error: native library can not be loaded for security reasons:\n " + theError.getMessage());
15
StActivity.exitWithError(this, "Broken apk?\n" + anInfo);
16
} catch(Exception theError) {
17
- anInfo.append("Error: unhandled exception:\n " + theError.getMessage());
18
+ java.io.StringWriter aStringWriter = new java.io.StringWriter();
19
+ theError.printStackTrace (new java.io.PrintWriter (aStringWriter));
20
+ anInfo.append("Error: unhandled exception:\n " + theError.getMessage()
21
+ + "\nCall stack:\n" + aStringWriter.toString());
22
StActivity.exitWithError(this, "Broken apk?\n" + anInfo);
23
}
24
25
updateHideSystemBars(myToHideStatusBar, myToHideNavBar);
26
+
27
+ // readOpenPath(false) should be called - NULLify intent afterwards
28
+ setIntent(null);
29
+ }
30
+
31
+ /**
32
+ * Request user permission.
33
+ */
34
+ protected void askUserPermission(String thePermission, String theRationale) {
35
+ // Dynamically load methods introduced by API level 23.
36
+ // On older system this permission is granted by user during application installation.
37
+ java.lang.reflect.Method aMetPtrCheckSelfPermission, aMetPtrRequestPermissions, aMetPtrShouldShowRequestPermissionRationale;
38
+ try {
39
+ aMetPtrCheckSelfPermission = myContext.getClass().getMethod("checkSelfPermission", String.class);
40
+ aMetPtrRequestPermissions = getClass().getMethod("requestPermissions", String[].class, int.class);
41
+ aMetPtrShouldShowRequestPermissionRationale = getClass().getMethod("shouldShowRequestPermissionRationale", String.class);
42
+ } catch(SecurityException theError) {
43
+ //postMessage("Unable to find permission methods:\n" + theError.getMessage());
44
+ return;
45
+ } catch(NoSuchMethodException theError) {
46
+ //postMessage("Unable to find permission methods:\n" + theError.getMessage());
47
+ return;
48
+ }
49
+
50
+ try {
51
+ //int isAlreadyGranted = myContext.checkSelfPermission(thePermission);
52
+ int isAlreadyGranted = (Integer )aMetPtrCheckSelfPermission.invoke(myContext, thePermission);
53
+ if(isAlreadyGranted == android.content.pm.PackageManager.PERMISSION_GRANTED) {
54
+ return;
55
+ }
56
+
57
+ //boolean toShowInfo = shouldShowRequestPermissionRationale(thePermission);
58
+ boolean toShowInfo = theRationale != null && (Boolean )aMetPtrShouldShowRequestPermissionRationale.invoke(this, thePermission);
59
+ if(toShowInfo) {
60
+ postMessage(theRationale);
61
+ }
62
+
63
+ // show dialog to user
64
+ //requestPermissions (new String[]{thePermission}, 0);
65
+ aMetPtrRequestPermissions.invoke(this, new String[]{thePermission}, 0);
66
+ } catch(IllegalArgumentException theError) {
67
+ postMessage("Internal error: Unable to call permission method:\n" + theError.getMessage());
68
+ return;
69
+ } catch(IllegalAccessException theError) {
70
+ postMessage("Internal error: Unable to call permission method:\n" + theError.getMessage());
71
+ return;
72
+ } catch(java.lang.reflect.InvocationTargetException theError) {
73
+ postMessage("Internal error: Unable to call permission method:\n" + theError.getMessage());
74
+ return;
75
+ }
76
}
77
78
/**
79
80
}
81
}
82
83
+ /**
84
+ * Redirect key event to C++ level.
85
+ */
86
+ @Override
87
+ public boolean dispatchKeyEvent(android.view.KeyEvent theEvent) {
88
+ if(super.dispatchKeyEvent(theEvent)) {
89
+ return true;
90
+ }
91
+ return myCppGlue != 0 && cppIsKeyOverridden(myCppGlue, theEvent.getKeyCode());
92
+ }
93
+
94
@Override
95
public void surfaceCreated(SurfaceHolder theHolder) {
96
super.surfaceCreated(theHolder);
97
98
//region Auxiliary methods
99
100
/**
101
+ * Action to play/pause.
102
+ */
103
+ public static final String THE_ACTION_PLAY_PAUSE = "ACTION_PLAY_PAUSE";
104
+
105
+ /**
106
+ * Action to open previous item in playlist.
107
+ */
108
+ public static final String THE_ACTION_PLAY_PREV = "ACTION_PLAY_PREV";
109
+
110
+ /**
111
+ * Action to open next item in playlist.
112
+ */
113
+ public static final String THE_ACTION_PLAY_NEXT = "ACTION_PLAY_NEXT";
114
+
115
+ /**
116
+ * Set playback action.
117
+ */
118
+ public boolean setPlaybackAction(Intent theIntent) {
119
+ if(myCppGlue == 0 || theIntent == null) {
120
+ return false;
121
+ }
122
+
123
+ if(THE_ACTION_PLAY_PAUSE.equals(theIntent.getAction())) {
124
+ cppSetOpenPath(myCppGlue, THE_ACTION_PLAY_PAUSE, "", false);
125
+ return true;
126
+ } else if(THE_ACTION_PLAY_PREV.equals(theIntent.getAction())) {
127
+ cppSetOpenPath(myCppGlue, THE_ACTION_PLAY_PREV, "", false);
128
+ return true;
129
+ } else if(THE_ACTION_PLAY_NEXT.equals(theIntent.getAction())) {
130
+ cppSetOpenPath(myCppGlue, THE_ACTION_PLAY_NEXT, "", false);
131
+ return true;
132
+ }
133
+ return false;
134
+ }
135
+
136
+ /**
137
* Read the open path from current intent and nullify it.
138
* This method is called by StAndroidGlue from C++.
139
*/
140
- protected void readOpenPath() {
141
+ protected void readOpenPath(boolean theToNullifyIntent) {
142
if(myCppGlue == 0) {
143
return;
144
}
145
146
Intent anIntent = getIntent();
147
- setIntent(null);
148
+ if(theToNullifyIntent) {
149
+ setIntent(null);
150
+ }
151
if(anIntent == null) {
152
cppSetOpenPath(myCppGlue, "", "", false);
153
return;
154
}
155
+ if(setPlaybackAction(anIntent)) {
156
+ return;
157
+ }
158
159
String anOpenPath = anIntent.getDataString();
160
String anOpenMime = anIntent.getType();
161
162
}
163
164
/**
165
+ * Set new activity title.
166
+ */
167
+ public void setWindowTitle(String theTitle) {
168
+ if(android.os.Build.VERSION.SDK_INT < 21) {
169
+ return;
170
+ }
171
+
172
+ final String aTitle = theTitle;
173
+ this.runOnUiThread (new Runnable() { public void run() {
174
+ //setTitle(aTitle); // sets window title, which we don't have...
175
+ setTaskDescription(new android.app.ActivityManager.TaskDescription(aTitle));
176
+ }});
177
+ }
178
+
179
+ /**
180
+ * Keep CPU on.
181
+ */
182
+ public void setPartialWakeLockOn(String theTitle, boolean theToLock) {
183
+ if(myWakeLock == null) {
184
+ return;
185
+ }
186
+
187
+ if(theToLock) {
188
+ myWakeLock.acquire();
189
+ } else if(myWakeLock.isHeld()) {
190
+ myWakeLock.release();
191
+ }
192
+ }
193
+
194
+ /**
195
* Method to turn stereo output on or off.
196
*/
197
public void setHardwareStereoOn(boolean theToEnable) {
198
199
private native void cppSetSwapEyes(long theCppPtr,
200
boolean theToSwap);
201
202
+ /**
203
+ * Return TRUE if key is processed by application.
204
+ */
205
+ private native boolean cppIsKeyOverridden(long theCppPtr,
206
+ int theKeyCode);
207
+
208
//endregion
209
210
@SuppressWarnings("deprecation")
211
212
//region class fields
213
214
protected ContextWrapper myContext;
215
+ protected android.os.PowerManager.WakeLock myWakeLock;
216
+
217
protected SensorManager mySensorMgr;
218
protected Sensor mySensorOri;
219
protected float myQuat[] = { 0.0f, 0.0f, 0.0f, 1.0f };
220
sview-17_04.tar.gz/sview/src/com/sview/StMovieActivity.java -> sview-20_08.tar.gz/sview/src/com/sview/StMovieActivity.java
Changed
71
1
2
public class StMovieActivity extends StActivity {
3
4
/**
5
+ * Global reference to activity for managing by background service.
6
+ */
7
+ public static StMovieActivity backgroundActivity;
8
+
9
+ /**
10
* Virtual method defining StApplication class.
11
*/
12
@Override
13
14
}
15
16
/**
17
+ * Return current title.
18
+ */
19
+ public String getCurrentTitle() {
20
+ return myCurrentTitle;
21
+ }
22
+
23
+ /**
24
* Create activity.
25
*/
26
@Override
27
28
super.onCreate(theSavedInstanceState);
29
}
30
31
+ /**
32
+ * Keep CPU on.
33
+ */
34
+ @Override
35
+ public void setPartialWakeLockOn(String theTitle, boolean theToLock) {
36
+ if(myWakeLock == null) {
37
+ return;
38
+ }
39
+
40
+ super.setPartialWakeLockOn(theTitle, theToLock);
41
+ if(android.os.Build.VERSION.SDK_INT < 24) {
42
+ return;
43
+ }
44
+
45
+ final String aTitle = theTitle;
46
+ final boolean toLock = theToLock;
47
+ final StMovieActivity aThis = this;
48
+ this.runOnUiThread(new Runnable() { public void run() {
49
+ // start a dummy foreground service, which actually does nothing but shows a system notification;
50
+ // this service (but the very existance) prevents system closing/suspending sView working threads playing audio in background
51
+ myCurrentTitle = aTitle;
52
+ android.content.Intent anIntent = new android.content.Intent(aThis, StMovieService.class);
53
+ if(toLock) {
54
+ backgroundActivity = aThis;
55
+ anIntent.setAction(toLock ? StMovieService.THE_ACTION_START_SERVICE : StMovieService.THE_ACTION_STOP_SERVICE);
56
+ if(android.os.Build.VERSION.SDK_INT >= 26) {
57
+ startForegroundService(anIntent);
58
+ } else {
59
+ startService(anIntent);
60
+ }
61
+ } else {
62
+ backgroundActivity = null;
63
+ stopService(anIntent);
64
+ }
65
+ }});
66
+ }
67
+
68
+ private String myCurrentTitle;
69
+
70
}
71
sview-20_08.tar.gz/sview/src/com/sview/StMovieService.java
Added
192
1
2
+/**
3
+ * This is source code for sView
4
+ *
5
+ * Copyright © Kirill Gavrilov, 2019
6
+ */
7
+package com.sview;
8
+
9
+import android.os.Bundle;
10
+
11
+/**
12
+ * Dummy foreground service for playing audio in background.
13
+ * Does nothing but shows a notification.
14
+ */
15
+public class StMovieService extends android.app.Service {
16
+
17
+ /**
18
+ * Action to start service.
19
+ */
20
+ public static final String THE_ACTION_START_SERVICE = "ACTION_START_SERVICE";
21
+
22
+ /**
23
+ * Action to stop service.
24
+ */
25
+ public static final String THE_ACTION_STOP_SERVICE = "ACTION_STOP_SERVICE";
26
+
27
+ /**
28
+ * Custom channel ID.
29
+ */
30
+ private final String THE_SVIEW_AUDIO_CHANNEL_ID = "com.sview.audio_channel";
31
+
32
+ /**
33
+ * Empty constructor.
34
+ */
35
+ public StMovieService() {
36
+ //
37
+ }
38
+
39
+ /**
40
+ * Create service.
41
+ */
42
+ @Override
43
+ public void onCreate() {
44
+ super.onCreate();
45
+ createNotificationChannel();
46
+ // should be started within several seconds, or will be killed by system
47
+ startForegroundService();
48
+ }
49
+
50
+ /**
51
+ * Destroy service.
52
+ */
53
+ @Override
54
+ public void onDestroy() {
55
+ //
56
+ }
57
+
58
+ /**
59
+ * Create binding.
60
+ */
61
+ @Override
62
+ public android.os.IBinder onBind(android.content.Intent theIntent) {
63
+ // we don't provide binding, so return null
64
+ return null;
65
+ }
66
+
67
+ /**
68
+ * Start a command.
69
+ */
70
+ @Override
71
+ public int onStartCommand(android.content.Intent theIntent, int theFlags, int theStartId) {
72
+ String anAction = theIntent != null ? theIntent.getAction() : THE_ACTION_STOP_SERVICE;
73
+ //android.widget.Toast.makeText(this, " @@ " + anAction, android.widget.Toast.LENGTH_LONG).show();
74
+ switch(anAction) {
75
+ case THE_ACTION_START_SERVICE: {
76
+ // if we get killed, after returning from here, restart
77
+ startForegroundService();
78
+ return START_STICKY;
79
+ }
80
+ case THE_ACTION_STOP_SERVICE: {
81
+ stopForegroundService();
82
+ return START_NOT_STICKY;
83
+ }
84
+ case StActivity.THE_ACTION_PLAY_PREV:
85
+ case StActivity.THE_ACTION_PLAY_NEXT:
86
+ case StActivity.THE_ACTION_PLAY_PAUSE: {
87
+ //android.widget.Toast.makeText(this, " $$ " + anAction, android.widget.Toast.LENGTH_LONG).show();
88
+ final StMovieActivity aMainActivity = StMovieActivity.backgroundActivity;
89
+ if(aMainActivity != null) {
90
+ aMainActivity.setPlaybackAction(theIntent);
91
+ }
92
+ return START_NOT_STICKY;
93
+ }
94
+ }
95
+ return START_NOT_STICKY;
96
+ }
97
+
98
+ /**
99
+ * Start foreground service - create notification.
100
+ */
101
+ private void startForegroundService() {
102
+ final StMovieActivity aMainActivity = StMovieActivity.backgroundActivity;
103
+ String anActiveItem = "Audio playback";
104
+ if(aMainActivity != null) {
105
+ anActiveItem = aMainActivity.getCurrentTitle();
106
+ }
107
+
108
+ android.content.Intent anIntent = new android.content.Intent(this, StMovieActivity.class);
109
+ android.app.PendingIntent aPendingIntent = android.app.PendingIntent.getActivity(this, 0, anIntent, 0);
110
+
111
+ android.app.Notification.Builder aNoti;
112
+ if(android.os.Build.VERSION.SDK_INT >= 26) {
113
+ aNoti = new android.app.Notification.Builder(this, THE_SVIEW_AUDIO_CHANNEL_ID);
114
+ } else {
115
+ aNoti = new android.app.Notification.Builder(this);
116
+ }
117
+ aNoti.setPriority(android.app.Notification.PRIORITY_LOW); // Android 8.0+ will use Notification Channel importance instead
118
+ //aNoti.setAutoCancel(true);
119
+ aNoti.setContentIntent(aPendingIntent); // intent on tapping notification
120
+ aNoti.setContentTitle(anActiveItem);
121
+ //aNoti.setContentText("");
122
+ aNoti.setSmallIcon(com.sview.R.drawable.ic_media_play);
123
+ //aNoti.setLargeIcon(aBitmap);
124
+
125
+ // add buttons (note that Android 7.0+ will NOT show action icons!)
126
+ {
127
+ android.content.Intent aPlayIntent = new android.content.Intent(this, StMovieService.class);
128
+ aPlayIntent.setAction(StActivity.THE_ACTION_PLAY_PREV);
129
+ android.app.PendingIntent aPendingPlayIntent = android.app.PendingIntent.getService(this, 0, aPlayIntent, 0);
130
+ aNoti.addAction(new android.app.Notification.Action(android.R.drawable.ic_media_previous,
131
+ android.os.Build.VERSION.SDK_INT >= 24
132
+ ? " \u23EE "
133
+ : "PREV",
134
+ aPendingPlayIntent));
135
+ }
136
+ {
137
+ android.content.Intent aPlayIntent = new android.content.Intent(this, StMovieService.class);
138
+ aPlayIntent.setAction(StActivity.THE_ACTION_PLAY_PAUSE);
139
+ android.app.PendingIntent aPendingPlayIntent = android.app.PendingIntent.getService(this, 0, aPlayIntent, 0);
140
+ aNoti.addAction(new android.app.Notification.Action(android.R.drawable.ic_media_pause,
141
+ android.os.Build.VERSION.SDK_INT >= 24
142
+ ? " \u23F9 " // " \u23F8 "
143
+ : "PAUSE", aPendingPlayIntent));
144
+ }
145
+ {
146
+ android.content.Intent aPlayIntent = new android.content.Intent(this, StMovieService.class);
147
+ aPlayIntent.setAction(StActivity.THE_ACTION_PLAY_NEXT);
148
+ android.app.PendingIntent aPendingPlayIntent = android.app.PendingIntent.getService(this, 0, aPlayIntent, 0);
149
+ aNoti.addAction(new android.app.Notification.Action(android.R.drawable.ic_media_next,
150
+ android.os.Build.VERSION.SDK_INT >= 24
151
+ ? " \u23ED "
152
+ : "NEXT",
153
+ aPendingPlayIntent));
154
+ }
155
+ final int aNotifId = 1; // unique ID, should not be 0
156
+ try {
157
+ startForeground(aNotifId, aNoti.build());
158
+ } catch(SecurityException theError) {
159
+ android.widget.Toast.makeText(this,
160
+ "Internal error: unable to start StMovieService.startForeground() due to security reasons:\n " + theError.getMessage(),
161
+ android.widget.Toast.LENGTH_LONG).show();
162
+ }
163
+ }
164
+
165
+ /**
166
+ * Stop foreground service and remove the notification.
167
+ */
168
+ private void stopForegroundService() {
169
+ stopForeground(true);
170
+ stopSelf();
171
+ }
172
+
173
+ /**
174
+ * Create the NotificationChannel (adjust settings of the channel).
175
+ */
176
+ private void createNotificationChannel() {
177
+ if(android.os.Build.VERSION.SDK_INT < 26) {
178
+ return;
179
+ }
180
+
181
+ android.app.NotificationChannel aChannel = new android.app.NotificationChannel(THE_SVIEW_AUDIO_CHANNEL_ID,
182
+ THE_SVIEW_AUDIO_CHANNEL_ID,
183
+ android.app.NotificationManager.IMPORTANCE_LOW);
184
+ aChannel.enableLights(false);
185
+ aChannel.enableVibration(false);
186
+ aChannel.setSound(null, null);
187
+ android.app.NotificationManager aNotifMgr = getSystemService(android.app.NotificationManager.class);
188
+ aNotifMgr.createNotificationChannel(aChannel);
189
+ }
190
+
191
+}
192
sview-17_04.tar.gz/sview/sview.cbp -> sview-20_08.tar.gz/sview/sview.cbp
Changed
32
1
2
<Unit filename="Resources/English.lproj/MainMenu.xib" />
3
<Unit filename="Resources/sView.icns" />
4
<Unit filename="Resources/sView_Media.icns" />
5
+ <Unit filename="src/com/sview/CrashReportActivity.java">
6
+ <Option compile="0" />
7
+ <Option link="0" />
8
+ </Unit>
9
+ <Unit filename="src/com/sview/MainActivity.java">
10
+ <Option compile="0" />
11
+ <Option link="0" />
12
+ </Unit>
13
+ <Unit filename="src/com/sview/StActivity.java">
14
+ <Option compile="0" />
15
+ <Option link="0" />
16
+ </Unit>
17
+ <Unit filename="src/com/sview/StImageActivity.java">
18
+ <Option compile="0" />
19
+ <Option link="0" />
20
+ </Unit>
21
+ <Unit filename="src/com/sview/StMovieActivity.java">
22
+ <Option compile="0" />
23
+ <Option link="0" />
24
+ </Unit>
25
+ <Unit filename="src/com/sview/StS3dvSurface.java">
26
+ <Option compile="0" />
27
+ <Option link="0" />
28
+ </Unit>
29
<Unit filename="StAppResponder.h">
30
<Option target="MAC_gcc" />
31
<Option target="MAC_gcc_DEBUG" />
32
sview-17_04.tar.gz/sview/sview.rc -> sview-20_08.tar.gz/sview/sview.rc
Changed
10
1
2
BEGIN
3
VALUE "FileDescription", "sView\000"
4
VALUE "FileVersion", SVIEW_SDK_VER_STRING "\000"
5
- VALUE "LegalCopyright", "\251 2007-2017 Kirill Gavrilov\000"
6
+ VALUE "LegalCopyright", "\251 2007-2020 Kirill Gavrilov and sView developers\000"
7
VALUE "ProductName", "sView\000"
8
VALUE "ProductVersion", SVIEW_SDK_VER_STRING "\000"
9
VALUE "OfficialSite", "www.sview.ru\000"
10