From bb958bb596517dbc110dd7454973a582fc470713 Mon Sep 17 00:00:00 2001 From: CavanSu <403029552@qq.com> Date: Sun, 8 Mar 2020 13:49:18 +0800 Subject: [PATCH 1/2] rtc_3.0.0 --- Group-Video/OpenVideoCall-Android/.gitignore | 5 + Group-Video/OpenVideoCall-Android/README.md | 14 +- Group-Video/OpenVideoCall-Android/README.yaml | 52 - .../OpenVideoCall-Android/README.zh.md | 24 +- .../OpenVideoCall-Android/README.zh.yaml | 54 - .../OpenVideoCall-Android/app/build.gradle | 4 +- .../io/agora/openvcall/AGApplication.java | 77 +- .../agora/openvcall/model/EngineConfig.java | 2 +- .../openvcall/model/MyEngineEventHandler.java | 341 +++-- .../agora/openvcall/model/WorkerThread.java | 299 ---- .../io/agora/openvcall/ui/BaseActivity.java | 124 +- .../io/agora/openvcall/ui/CallActivity.java | 58 +- .../io/agora/openvcall/ui/MainActivity.java | 2 +- .../openvcall/ui/NetworkTestActivity.java | 4 +- .../src/main/res/values/strings_config.xml | 2 +- Group-Video/OpenVideoCall-Android/ci.env.py | 16 +- Group-Video/OpenVideoCall-Web/README.md | 15 +- Group-Video/OpenVideoCall-Web/README.yaml | 40 - Group-Video/OpenVideoCall-Web/README.zh.md | 10 +- Group-Video/OpenVideoCall-Web/README.zh.yaml | 38 - Group-Video/OpenVideoCall-Windows/.gitignore | 12 + .../ChineseSimplified/ChineseSimplified.cpp | 73 - .../ChineseSimplified/ChineseSimplified.h | 80 -- .../ChineseSimplified.vcxproj | 190 --- .../ChineseSimplified.vcxproj.filters | 47 - .../Language/ChineseSimplified/Source.def | 66 - .../Language/ChineseSimplified/dllmain.cpp | 19 - .../Language/ChineseSimplified/stdafx.cpp | 8 - .../Language/ChineseSimplified/stdafx.h | 14 - .../Language/ChineseSimplified/targetver.h | 8 - .../Language/English/English.cpp | 73 - .../Language/English/English.h | 79 -- .../Language/English/English.vcxproj | 190 --- .../Language/English/English.vcxproj.filters | 47 - .../Language/English/Source.def | 66 - .../Language/English/dllmain.cpp | 19 - .../Language/English/stdafx.cpp | 8 - .../Language/English/stdafx.h | 16 - .../Language/English/targetver.h | 8 - .../OpenVideoCall-Windows/OpenVideoCall.pro | 76 + .../OpenVideoCall-Windows/OpenVideoCall.sln | 58 - .../OpenVideoCall/AGButton.cpp | 308 ----- .../OpenVideoCall/AGButton.h | 72 - .../OpenVideoCall/AGComboBox.cpp | 682 --------- .../OpenVideoCall/AGComboBox.h | 158 --- .../OpenVideoCall/AGConfig.cpp | 155 --- .../OpenVideoCall/AGConfig.h | 29 - .../OpenVideoCall/AGDesktopCaptureDlg.cpp | 229 --- .../OpenVideoCall/AGDesktopCaptureDlg.h | 57 - .../OpenVideoCall/AGEdit.cpp | 196 --- .../OpenVideoCall/AGEdit.h | 52 - .../OpenVideoCall/AGEngineEventHandler.cpp | 379 ----- .../OpenVideoCall/AGEngineEventHandler.h | 55 - .../OpenVideoCall/AGEventDef.h | 255 ---- .../OpenVideoCall/AGHyperLink.cpp | 177 --- .../OpenVideoCall/AGHyperLink.h | 45 - .../OpenVideoCall/AGLinkCtrl.cpp | 137 -- .../OpenVideoCall/AGLinkCtrl.h | 35 - .../OpenVideoCall/AGMessage.h | 9 - .../OpenVideoCall/AGResourceVisitor.cpp | 81 -- .../OpenVideoCall/AGResourceVisitor.h | 14 - .../OpenVideoCall/AGScreenCaptureDlg.cpp | 210 --- .../OpenVideoCall/AGScreenCaptureDlg.h | 43 - .../OpenVideoCall/AGSliderCtrl.cpp | 202 --- .../OpenVideoCall/AGSliderCtrl.h | 45 - .../OpenVideoCall/AGVideoTestWnd.cpp | 114 -- .../OpenVideoCall/AGVideoTestWnd.h | 45 - .../OpenVideoCall/AGVideoWnd.cpp | 357 ----- .../OpenVideoCall/AGVideoWnd.h | 104 -- .../OpenVideoCall/AgoraAudInputManager.cpp | 165 --- .../OpenVideoCall/AgoraAudInputManager.h | 29 - .../OpenVideoCall/AgoraCameraManager.cpp | 134 -- .../OpenVideoCall/AgoraCameraManager.h | 26 - .../OpenVideoCall/AgoraObject.cpp | 621 --------- .../OpenVideoCall/AgoraObject.h | 137 -- .../OpenVideoCall/AgoraPlayoutManager.cpp | 167 --- .../OpenVideoCall/AgoraPlayoutManager.h | 29 - .../OpenVideoCall/ChatDlg.cpp | 129 -- .../OpenVideoCall/ChatDlg.h | 37 - .../OpenVideoCall/DeviceDlg.cpp | 385 ------ .../OpenVideoCall/DeviceDlg.h | 82 -- .../OpenVideoCall/DskcapsetDlg.cpp | 120 -- .../OpenVideoCall/DskcapsetDlg.h | 41 - .../OpenVideoCall/EnterChannelDlg.cpp | 229 --- .../OpenVideoCall/EnterChannelDlg.h | 58 - .../OpenVideoCall/LanguageSet.cpp | 108 -- .../OpenVideoCall/LanguageSet.h | 29 - .../OpenVideoCall/LogoDlg.cpp | 168 --- .../OpenVideoCall/LogoDlg.h | 48 - .../OpenVideoCall/OpenVideoCall.cpp | 112 -- .../OpenVideoCall/OpenVideoCall.h | 32 - .../OpenVideoCall/OpenVideoCall.rc | Bin 26802 -> 0 bytes .../OpenVideoCall/OpenVideoCall.vcxproj | 375 ----- .../OpenVideoCall.vcxproj.filters | 441 ------ .../OpenVideoCall/OpenVideoCall.vcxproj.user | 4 - .../OpenVideoCall/OpenVideoCallDlg.cpp | 362 ----- .../OpenVideoCall/OpenVideoCallDlg.h | 82 -- .../OpenVideoCall/SetupDlg.cpp | 277 ---- .../OpenVideoCall/SetupDlg.h | 71 - .../OpenVideoCall/VideoDlg.cpp | 1230 ----------------- .../OpenVideoCall/VideoDlg.h | 180 --- .../res/IDB_BACKGROUND_VIDEO.bmp | Bin 27704 -> 0 bytes .../OpenVideoCall/res/IDB_BTNAUDIO_VIDEO.bmp | Bin 27702 -> 0 bytes .../OpenVideoCall/res/IDB_BTNCLOSE.bmp | Bin 5862 -> 0 bytes .../res/IDB_BTNENDCALL_VIDEO.bmp | Bin 27702 -> 0 bytes .../res/IDB_BTNFULLSCR_VIDEO.bmp | Bin 6966 -> 0 bytes .../OpenVideoCall/res/IDB_BTNMAUDIO_VIDEO.bmp | Bin 27702 -> 0 bytes .../OpenVideoCall/res/IDB_BTNMAX.bmp | Bin 5862 -> 0 bytes .../OpenVideoCall/res/IDB_BTNMIN.bmp | Bin 5862 -> 0 bytes .../OpenVideoCall/res/IDB_BTNMORE_VIDEO.bmp | Bin 27704 -> 0 bytes .../OpenVideoCall/res/IDB_BTNMSG_VIDEO.bmp | Bin 27704 -> 0 bytes .../OpenVideoCall/res/IDB_BTNNORSCR_VIDEO.bmp | Bin 6966 -> 0 bytes .../OpenVideoCall/res/IDB_BTNRESTORE.bmp | Bin 5862 -> 0 bytes .../OpenVideoCall/res/IDB_BTNSCRCAP_VIDEO.bmp | Bin 27702 -> 0 bytes .../OpenVideoCall/res/IDB_BTNSETUP_VIDEO.bmp | Bin 6966 -> 0 bytes .../OpenVideoCall/res/IDB_BTNTIP_VIDEO.bmp | Bin 6966 -> 0 bytes .../OpenVideoCall/res/IDB_BTNVIDEO_VIDEO.bmp | Bin 27702 -> 0 bytes .../OpenVideoCall/res/IDB_CMBBTN.bmp | Bin 1350 -> 0 bytes .../OpenVideoCall/res/IDB_CMBSEL.bmp | Bin 630 -> 0 bytes .../res/IDB_DESKTOPSHARE_VIDEO.bmp | Bin 63276 -> 0 bytes .../OpenVideoCall/res/IDB_DLG_LOGO.bmp | Bin 1080056 -> 0 bytes .../OpenVideoCall/res/IDB_DLG_MAIN.bmp | Bin 1080056 -> 0 bytes .../OpenVideoCall/res/IDB_LOGO.bmp | Bin 28568 -> 0 bytes .../OpenVideoCall/res/IDB_MENU_DEVICE.bmp | Bin 822 -> 0 bytes .../OpenVideoCall/res/IDB_MENU_FILTER.bmp | Bin 822 -> 0 bytes .../OpenVideoCall/res/IDB_MENU_INFO.bmp | Bin 822 -> 0 bytes .../OpenVideoCall/res/IDB_MENU_MORE.bmp | Bin 2358 -> 0 bytes .../OpenVideoCall/res/IDB_NETWORK_QUALITY.bmp | Bin 21558 -> 0 bytes .../OpenVideoCall/res/IDB_SLD_HOVER.bmp | Bin 1782 -> 0 bytes .../OpenVideoCall/res/IDB_SLD_NORMAL.bmp | Bin 1782 -> 0 bytes .../OpenVideoCall/res/ID_TEST_AUDIO.wav | Bin 244886 -> 0 bytes .../OpenVideoCall/res/OpenVideoCall.ico | Bin 33324 -> 0 bytes .../OpenVideoCall/res/OpenVideoCall.rc2 | Bin 812 -> 0 bytes .../OpenVideoCall/resource.h | Bin 12336 -> 0 bytes .../OpenVideoCall/stdafx.cpp | 8 - .../OpenVideoCall/stdafx.h | 59 - .../OpenVideoCall/targetver.h | 8 - .../video_preprocessing_plugin.cpp | 94 -- .../video_preprocessing_plugin.h | 10 - Group-Video/OpenVideoCall-Windows/README.md | 8 +- .../OpenVideoCall-Windows/README.zh.md | 10 +- .../OpenVideoCall-Windows/agoraconfig.cpp | 97 ++ .../OpenVideoCall-Windows/agoraconfig.h | 39 + .../OpenVideoCall-Windows/agoraobject.cpp | 465 +++++++ .../OpenVideoCall-Windows/agoraobject.h | 89 ++ .../agorawindowmanager.cpp | 47 + .../agorawindowmanager.h | 38 + .../OpenVideoCall-Windows/avdevice.cpp | 395 ++++++ Group-Video/OpenVideoCall-Windows/avdevice.h | 71 + Group-Video/OpenVideoCall-Windows/avdevice.ui | 1229 ++++++++++++++++ .../OpenVideoCall-Windows/build_release.bat | 24 + .../OpenVideoCall-Windows/enterroom.cpp | 195 +++ Group-Video/OpenVideoCall-Windows/enterroom.h | 68 + .../OpenVideoCall-Windows/enterroom.ui | 295 ++++ Group-Video/OpenVideoCall-Windows/inroom.cpp | 388 ++++++ Group-Video/OpenVideoCall-Windows/inroom.h | 109 ++ Group-Video/OpenVideoCall-Windows/inroom.ui | 98 ++ .../OpenVideoCall-Windows/inroomdig.cpp | 61 + Group-Video/OpenVideoCall-Windows/inroomdig.h | 26 + .../OpenVideoCall-Windows/inroomdig.ui | 22 + Group-Video/OpenVideoCall-Windows/main.cpp | 32 + .../OpenVideoCall-Windows/nettestdetail.cpp | 80 ++ .../OpenVideoCall-Windows/nettestdetail.h | 51 + .../OpenVideoCall-Windows/nettestdetail.ui | 283 ++++ .../OpenVideoCall-Windows/nettesting.cpp | 96 ++ .../OpenVideoCall-Windows/nettesting.h | 55 + .../OpenVideoCall-Windows/nettesting.ui | 126 ++ .../OpenVideoCall-Windows/nettestresult.cpp | 113 ++ .../OpenVideoCall-Windows/nettestresult.h | 61 + .../OpenVideoCall-Windows/nettestresult.ui | 241 ++++ .../OpenVideoCall-Windows/openvideocall.cpp | 116 ++ .../OpenVideoCall-Windows/openvideocall.h | 55 + .../OpenVideoCall-Windows/openvideocall.ico | Bin 0 -> 4286 bytes .../OpenVideoCall-Windows/openvideocall.qrc | 50 + .../OpenVideoCall-Windows/openvideocall.rc | 1 + .../OpenVideoCall-Windows/openvideocall.ui | 252 ++++ .../uiresource/OVC-win-03.jpg | Bin 0 -> 1152181 bytes .../uiresource/OVC-win-config.png | Bin 0 -> 67255 bytes .../uiresource/OVC-win-home.png | Bin 0 -> 72433 bytes .../uiresource/OVC-win-more users.jpg | Bin 0 -> 1031459 bytes .../uiresource/OVC-win-netdetail.png | Bin 0 -> 72801 bytes .../uiresource/OVC-win-netresult.png | Bin 0 -> 75716 bytes .../uiresource/OVC-win-nettest.png | Bin 0 -> 63549 bytes .../uiresource/allmute remote.png | Bin 0 -> 7370 bytes .../uiresource/allmute.png | Bin 0 -> 42379 bytes .../uiresource/box-01.png | Bin 0 -> 200 bytes .../uiresource/dropdow-01.png | Bin 0 -> 293 bytes .../uiresource/dropdown-02.png | Bin 0 -> 289 bytes .../uiresource/dropdown-03.png | Bin 0 -> 310 bytes .../OpenVideoCall-Windows/uiresource/edit.png | Bin 0 -> 367 bytes .../uiresource/edit1.png | Bin 0 -> 367 bytes .../uiresource/edit2.png | Bin 0 -> 364 bytes .../uiresource/edit3.png | Bin 0 -> 193 bytes .../uiresource/edit4.png | Bin 0 -> 180 bytes .../uiresource/edit5.png | Bin 0 -> 226 bytes .../OpenVideoCall-Windows/uiresource/gray.png | Bin 0 -> 888 bytes .../uiresource/icon-back hover.png | Bin 0 -> 485 bytes .../uiresource/icon-back.png | Bin 0 -> 487 bytes .../uiresource/icon-camera off.png | Bin 0 -> 1761 bytes .../uiresource/icon-camera on.png | Bin 0 -> 1509 bytes .../uiresource/icon-camera.png | Bin 0 -> 1049 bytes .../uiresource/icon-close default.png | Bin 0 -> 366 bytes .../uiresource/icon-close hover.png | Bin 0 -> 384 bytes .../uiresource/icon-hang up hover.png | Bin 0 -> 1265 bytes .../uiresource/icon-hang up.png | Bin 0 -> 1861 bytes .../uiresource/icon-loading.png | Bin 0 -> 2033 bytes .../uiresource/icon-micorophone off.png | Bin 0 -> 1644 bytes .../uiresource/icon-micorophone on.png | Bin 0 -> 1286 bytes .../uiresource/icon-micorophone.png | Bin 0 -> 995 bytes .../uiresource/icon-min default.png | Bin 0 -> 141 bytes .../uiresource/icon-min hover.png | Bin 0 -> 145 bytes .../uiresource/icon-setting hover.png | Bin 0 -> 1007 bytes .../uiresource/icon-setting.png | Bin 0 -> 965 bytes .../uiresource/loading.gif | Bin 0 -> 30772 bytes .../uiresource/mutevideo remote.png | Bin 0 -> 3971 bytes .../uiresource/mutevideo.png | Bin 0 -> 13155 bytes .../uiresource/pic-bad.png | Bin 0 -> 9309 bytes .../uiresource/pic-good.png | Bin 0 -> 8327 bytes .../uiresource/pic-poor.png | Bin 0 -> 8128 bytes .../OpenVideoCall-Windows/uiresource/qlabel.h | 157 +++ .../uiresource/slider.png | Bin 0 -> 3936 bytes .../uiresource/switch-off.png | Bin 0 -> 1269 bytes .../uiresource/switch-open.png | Bin 0 -> 1363 bytes .../OpenVideoCall.xcodeproj/project.pbxproj | 84 +- .../OpenVideoCall/Base.lproj/Main.storyboard | 65 +- .../OpenVideoCall/DimensionCell.h | 2 +- .../OpenVideoCall/LastmileViewController.h | 2 +- .../OpenVideoCall/LastmileViewController.m | 23 +- .../OpenVideoCall/MainViewController.m | 11 + .../OpenVideoCall/RoomOptionsViewController.m | 7 + .../OpenVideoCall/RoomViewController.h | 2 +- .../OpenVideoCall/Settings.h | 2 +- .../OpenVideoCall/SettingsViewController.h | 2 +- .../OpenVideoCall/SettingsViewController.m | 16 +- .../OpenVideoCall/VideoSession.h | 2 +- .../OpenVideoCall-iOS-Objective-C/README.md | 35 +- .../README.zh.md | 39 +- .../OpenVideoCall-iOS-Objective-C/ci.env.py | 26 - .../OpenVideoCall-iOS-Objective-C/clear.sh | 6 + .../OpenVideoCall.xcodeproj/project.pbxproj | 174 ++- .../AGEVideoLayout/AGEEventsObserver.swift | 53 + .../AGEVideoLayout/AGEVideoConstraints.swift | 233 ++++ .../AGEVideoLayout/AGEVideoContainer.swift | 762 ++++++++++ .../AGEVideoLayout/AGEVideoLayout.swift | 353 +++++ .../AGEVideoLayout}/AGEView.swift | 60 + .../ActivityViewController.swift | 31 - .../{MediaInfo.swift => AgoraExtension.swift} | 62 +- .../OpenVideoCall/Base.lproj/Main.storyboard | 74 +- .../OpenVideoCall/Info.plist | 2 - .../LastmileViewController.swift | 21 +- .../OpenVideoCall/MainViewController.swift | 12 +- .../OpenVideoCall/MediaCharacter.swift | 2 + .../OpenVideoCall-Bridging-Header.h | 5 - .../RoomOptionsViewController.swift | 6 + .../OpenVideoCall/RoomViewController.swift | 156 +-- .../OpenVideoCall/Settings.swift | 2 +- .../SettingsViewController.swift | 15 +- .../OpenVideoCall/StatisticsInfo.swift | 117 ++ .../OpenVideoCall/VideoSession.swift | 81 +- .../OpenVideoCall/VideoView.swift | 48 +- .../OpenVideoCall/VideoViewLayouter.swift | 343 ----- Group-Video/OpenVideoCall-iOS/README.md | 32 +- Group-Video/OpenVideoCall-iOS/README.zh.md | 35 +- Group-Video/OpenVideoCall-iOS/ci.env.py | 26 - Group-Video/OpenVideoCall-iOS/clear.sh | 6 + .../OpenVideoCall.xcodeproj/project.pbxproj | 76 +- .../OpenVideoCall/AGEVideoContainer.swift | 544 -------- .../OpenVideoCall/AGEVideoLayout.swift | 244 ---- .../AGEVideoLayout/AGEEventsObserver.swift | 53 + .../AGEVideoLayout/AGEVideoConstraints.swift | 233 ++++ .../AGEVideoLayout/AGEVideoContainer.swift | 762 ++++++++++ .../AGEVideoLayout/AGEVideoLayout.swift | 353 +++++ .../AGEVideoLayout/AGEView.swift | 183 +++ .../OpenVideoCall/AgoraExtension.swift | 2 +- .../LastmileViewController.swift | 2 +- .../OpenVideoCall/MainViewController.swift | 2 +- .../OpenVideoCall/RoomViewController.swift | 16 +- .../OpenVideoCall/Settings.swift | 2 +- .../SettingsViewController.swift | 2 +- .../OpenVideoCall/StatisticsInfo.swift | 2 +- .../OpenVideoCall/VideoSession.swift | 2 +- Group-Video/OpenVideoCall-macOS/README.md | 42 +- Group-Video/OpenVideoCall-macOS/README.zh.md | 37 +- Group-Video/OpenVideoCall-macOS/ci.env.py | 18 - Group-Video/OpenVideoCall-macOS/clear.sh | 6 + LICENSE.md | 10 - .../Agora-Android-Tutorial-1to1/.gitignore | 5 + .../Agora-Android-Tutorial-1to1/README.md | 22 +- .../Agora-Android-Tutorial-1to1/README.yaml | 51 - .../Agora-Android-Tutorial-1to1/README.zh.md | 29 +- .../README.zh.yaml | 57 - .../.gitignore | 5 + .../README.md | 20 +- .../README.yaml | 52 - .../README.zh.md | 28 +- .../README.zh.yaml | 57 - .../Agora-Web-Tutorial-1to1-React/README.md | 9 +- .../README.zh.md | 10 +- .../Agora-Web-Tutorial-1to1-Webpack/README.md | 9 +- .../README.yaml | 42 - .../README.zh.md | 10 +- .../README.zh.yaml | 47 - .../Agora-Web-Tutorial-1to1/README.md | 21 +- .../Agora-Web-Tutorial-1to1/README.yaml | 35 - .../Agora-Web-Tutorial-1to1/README.zh.md | 17 +- .../Agora-Web-Tutorial-1to1/README.zh.yaml | 41 - .../Agora-Web-Tutorial-1to1/index.html | 2 +- .../Agora-Windows-Tutorial-1to1/README.md | 37 +- .../Agora-Windows-Tutorial-1to1/README.zh.md | 16 +- .../contents.xcworkspacedata | 7 - .../.xcodesamplecode.plist | 0 .../project.pbxproj | 179 +-- .../contents.xcworkspacedata | 7 + .../xcshareddata/IDEWorkspaceChecks.plist | 0 .../Agora-iOS-Tutorial-Objective-C.xcscheme | 78 ++ .../AppDelegate.h | 0 .../AppDelegate.m | 0 .../AppID.h | 0 .../AppID.m | 0 .../AppIcon.appiconset/Contents.json | 0 .../Assets.xcassets/Contents.json | 0 .../hangUpButton.imageset/Contents.json | 0 .../hangUpButton.imageset/hangup.png | Bin .../localVideoMutedBg.imageset/Contents.json | 0 .../localVideoMutedBg.imageset/cameramute.png | Bin .../muteButton.imageset/Contents.json | 0 .../muteButton.imageset/mute.png | Bin .../muteButtonSelected.imageset/Contents.json | 0 .../muteButtonSelected.imageset/unmute.png | Bin .../switchCameraButton.imageset/Contents.json | 0 .../switch_camera.png | Bin .../Contents.json | 0 .../unswitch-camera.png | Bin .../videoMuteButton.imageset/Contents.json | 0 .../videoMuteButton.imageset/cameraoff.png | Bin .../Contents.json | 0 .../cameraoff copy.png | Bin .../Contents.json | 0 .../cameraoff_mainVideo.png | Bin .../Base.lproj/LaunchScreen.storyboard | 0 .../Base.lproj/Main.storyboard | 0 .../Info.plist | 0 .../VideoChatViewController.h | 2 +- .../VideoChatViewController.m | 0 .../main.m | 0 .../README.md | 11 +- .../README.zh.md | 25 +- .../build.sh | 4 +- .../ci.env.py | 18 +- .../clear.sh | 6 + .../contents.xcworkspacedata | 7 - .../.xcodesamplecode.plist | 0 .../project.pbxproj | 148 +- .../contents.xcworkspacedata | 7 + .../xcshareddata/IDEWorkspaceChecks.plist | 0 .../xcschemes/Agora-iOS-Tutorial.xcscheme} | 32 +- .../AppDelegate.swift | 0 .../AppID.swift | 0 .../AppIcon.appiconset/Contents.json | 0 .../Assets.xcassets/Contents.json | 0 ...8D9B541-3C15-4F3F-B817-1BFA03224F58@1x.png | Bin ...8D9B541-3C15-4F3F-B817-1BFA03224F58@2x.png | Bin ...8D9B541-3C15-4F3F-B817-1BFA03224F58@3x.png | Bin .../big_logo.imageset/Contents.json | 0 .../call.imageset/Contents.json | 0 .../Assets.xcassets/call.imageset/call@4x.png | Bin .../call_pressed.imageset/Contents.json | 0 .../call_pressed.imageset/call_pressed@4x.png | Bin .../end.imageset/Contents.json | 0 .../Assets.xcassets/end.imageset/end@4x.png | Bin .../end_pressed.imageset/Contents.json | 0 .../end_pressed.imageset/end_pressed@4x.png | Bin .../gray_bg.imageset/Contents.json | 0 .../gray_bg.imageset/gray_bg@1x.png | Bin .../gray_bg.imageset/gray_bg@2x.png | Bin .../gray_bg.imageset/gray_bg@3x.png | Bin ...A1BE415-1E76-4F1B-AD85-3C21C4E0DCDE@1x.png | Bin ...A1BE415-1E76-4F1B-AD85-3C21C4E0DCDE@2x.png | Bin ...A1BE415-1E76-4F1B-AD85-3C21C4E0DCDE@3x.png | Bin .../logo.imageset/Contents.json | 0 .../mic.imageset/Contents.json | 0 .../Assets.xcassets/mic.imageset/mic@4x.png | Bin .../mic_pressed.imageset/Contents.json | 0 .../mic_pressed.imageset/mic_pressed@4x.png | Bin .../mute.imageset/Contents.json | 0 .../Assets.xcassets/mute.imageset/mute@4x.png | Bin .../mute_pressed.imageset/Contents.json | 0 .../mute_pressed.imageset/mute_pressed@4x.png | Bin .../switch.imageset/Contents.json | 0 .../switch.imageset/switch@4x.png | Bin .../switch_pressed.imageset/Contents.json | 0 .../switch_pressed@4x.png | Bin .../Base.lproj/LaunchScreen.storyboard | 0 .../Base.lproj/Main.storyboard | 0 .../Info.plist | 0 .../Log.storyboard | 0 .../LogViewController.swift | 0 .../VideoChatViewController.swift | 2 +- .../Agora-iOS-Tutorial-Swift-1to1/README.md | 28 +- .../README.zh.md | 23 +- .../Agora-iOS-Tutorial-Swift-1to1/build.sh | 4 +- .../Agora-iOS-Tutorial-Swift-1to1/ci.env.py | 38 +- .../Agora-iOS-Tutorial-Swift-1to1/clear.sh | 6 + .../.gitignore | 108 ++ .../.xcodesamplecode.plist | 0 .../project.pbxproj | 445 ++++++ .../AppDelegate.swift | 32 + .../AppID.swift | 18 + .../AppIcon.appiconset/Contents.json | 98 ++ .../Assets.xcassets/Contents.json | 0 .../big_logo.imageset/Contents.json | 23 + .../big_logo.imageset/big_logo.png | Bin 0 -> 8438 bytes .../big_logo.imageset/big_logo@2x.png | Bin 0 -> 22429 bytes .../big_logo.imageset/big_logo@3x.png | Bin 0 -> 42540 bytes .../call.imageset/Contents.json | 15 + .../Assets.xcassets/call.imageset/call@4x.png | Bin 0 -> 19713 bytes .../end.imageset/Contents.json | 15 + .../Assets.xcassets/end.imageset/end@4x.png | Bin 0 -> 29153 bytes .../localBackColor.colorset/Contents.json | 20 + .../logErrorColor.colorset/Contents.json | 20 + .../logInfoColor.colorset/Contents.json | 20 + .../logWarningColor.colorset/Contents.json | 20 + .../logo.imageset/Contents.json | 23 + .../Assets.xcassets/logo.imageset/logo@1x.png | Bin 0 -> 2411 bytes .../Assets.xcassets/logo.imageset/logo@2x.png | Bin 0 -> 6299 bytes .../Assets.xcassets/logo.imageset/logo@3x.png | Bin 0 -> 10884 bytes .../mic.imageset/Contents.json | 15 + .../Assets.xcassets/mic.imageset/mic@4x.png | Bin 0 -> 15558 bytes .../mute.imageset/Contents.json | 15 + .../Assets.xcassets/mute.imageset/mute@4x.png | Bin 0 -> 16991 bytes .../remoteBackColor.colorset/Contents.json | 20 + .../switch.imageset/Contents.json | 15 + .../switch.imageset/switch@4x.png | Bin 0 -> 16853 bytes .../Base.lproj/LaunchScreen.storyboard | 25 + .../ContentView.swift | 159 +++ .../Info.plist | 60 + .../Preview Assets.xcassets}/Contents.json | 0 .../SceneDelegate.swift | 60 + .../VideoCanvas.swift | 26 + .../VideoEngine.swift | 59 + .../VideoSessionView.swift | 47 + .../Agora-iOS-Tutorial-SwiftUI-1to1/README.md | 61 + .../README.zh.md | 63 + .../Agora-iOS-Tutorial-SwiftUI-1to1/build.sh | 17 + .../Agora-iOS-Tutorial-SwiftUI-1to1/ci.env.py | 24 + .../Agora-iOS-Tutorial-SwiftUI-1to1/clear.sh | 6 + .../exportPlist.plist | 15 + .../contents.xcworkspacedata | 7 - .../.xcodesamplecode.plist | 0 .../project.pbxproj | 148 +- .../contents.xcworkspacedata | 7 + .../xcshareddata/IDEWorkspaceChecks.plist | 0 .../Agora-Mac-Tutorial-Objective-C.xcscheme | 78 ++ .../AppDelegate.h | 0 .../AppDelegate.m | 0 .../AppID.h | 0 .../AppID.m | 0 .../AppIcon.appiconset/Contents.json | 0 .../Assets.xcassets/Contents.json | 6 + .../Contents.json | 0 .../device_selection.png | Bin .../hangUpButton.imageset/Contents.json | 0 .../hangUpButton.imageset/hangup.png | Bin .../localVideoMutedBg.imageset/Contents.json | 0 .../cameramutehorizontal.png | Bin .../muteButton.imageset/Contents.json | 0 .../muteButton.imageset/mute.png | Bin .../muteButtonSelected.imageset/Contents.json | 0 .../muteButtonSelected.imageset/unmute.png | Bin .../screenShareButton.imageset/Contents.json | 0 .../screen_sharing.png | Bin .../Contents.json | 0 .../unscreen_share.png | Bin .../videoMuteButton.imageset/Contents.json | 0 .../videoMuteButton.imageset/cameraoff.png | Bin .../Contents.json | 0 .../cameraon.png | Bin .../Contents.json | 0 .../cameraoff_mainVideo.png | Bin .../Base.lproj/Main.storyboard | 42 +- .../DeviceSelectionViewController.h | 2 +- .../DeviceSelectionViewController.m | 0 .../Info.plist | 0 .../VideoChatViewController.h | 2 +- .../VideoChatViewController.m | 0 .../main.m | 0 .../README.md | 23 +- .../README.zh.md | 25 +- .../build.sh | 4 +- .../ci.env.py | 20 +- .../clear.sh | 6 + .../contents.xcworkspacedata | 7 - .../.xcodesamplecode.plist | 2 + .../project.pbxproj | 134 +- .../contents.xcworkspacedata | 7 + .../xcshareddata/IDEWorkspaceChecks.plist | 0 .../Agora-Mac-Tutorial-Swift.xcscheme | 78 ++ .../AppDelegate.swift | 0 .../AppID.swift | 0 .../AppIcon.appiconset/Contents.json | 0 .../Assets.xcassets/Contents.json | 6 + .../Contents.json | 0 .../device_selection.png | Bin .../hangUpButton.imageset/Contents.json | 0 .../hangUpButton.imageset/hangup.png | Bin .../localVideoMutedBg.imageset/Contents.json | 0 .../cameramutehorizontal.png | Bin .../muteButton.imageset/Contents.json | 0 .../muteButton.imageset/mute.png | Bin .../muteButtonSelected.imageset/Contents.json | 0 .../muteButtonSelected.imageset/unmute.png | Bin .../screenShareButton.imageset/Contents.json | 0 .../screen_sharing.png | Bin .../Contents.json | 0 .../unscreen_share.png | Bin .../videoMuteButton.imageset/Contents.json | 0 .../videoMuteButton.imageset/cameraoff.png | Bin .../Contents.json | 0 .../cameraon.png | Bin .../Contents.json | 0 .../cameraoff_mainVideo.png | Bin .../Base.lproj/Main.storyboard | 0 .../DeviceSelectionViewController.swift | 2 +- .../Info.plist | 0 .../VideoChatViewController.swift | 2 +- .../Agora-macOS-Tutorial-Swift-1to1/README.md | 24 +- .../README.zh.md | 13 +- .../Agora-macOS-Tutorial-Swift-1to1/build.sh | 4 +- .../Agora-macOS-Tutorial-Swift-1to1/ci.env.py | 17 +- .../Agora-macOS-Tutorial-Swift-1to1/clear.sh | 6 + README.md | 64 - azure-pipelines.yml | 39 +- cicd/scripts/sdkdownload.sh | 68 + cicd/templates/build-android.yml | 9 +- cicd/templates/build-ios.yml | 12 +- cicd/templates/build-mac.yml | 10 +- cicd/templates/github-release.yml | 9 - gen_readme.sh | 4 - gen_readme_all.sh | 16 - 539 files changed, 12398 insertions(+), 15142 deletions(-) delete mode 100644 Group-Video/OpenVideoCall-Android/README.yaml delete mode 100644 Group-Video/OpenVideoCall-Android/README.zh.yaml delete mode 100644 Group-Video/OpenVideoCall-Android/app/src/main/java/io/agora/openvcall/model/WorkerThread.java delete mode 100644 Group-Video/OpenVideoCall-Web/README.yaml delete mode 100644 Group-Video/OpenVideoCall-Web/README.zh.yaml create mode 100644 Group-Video/OpenVideoCall-Windows/.gitignore delete mode 100644 Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/ChineseSimplified.cpp delete mode 100644 Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/ChineseSimplified.h delete mode 100644 Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/ChineseSimplified.vcxproj delete mode 100644 Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/ChineseSimplified.vcxproj.filters delete mode 100644 Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/Source.def delete mode 100644 Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/dllmain.cpp delete mode 100644 Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/stdafx.cpp delete mode 100644 Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/stdafx.h delete mode 100644 Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/targetver.h delete mode 100644 Group-Video/OpenVideoCall-Windows/Language/English/English.cpp delete mode 100644 Group-Video/OpenVideoCall-Windows/Language/English/English.h delete mode 100644 Group-Video/OpenVideoCall-Windows/Language/English/English.vcxproj delete mode 100644 Group-Video/OpenVideoCall-Windows/Language/English/English.vcxproj.filters delete mode 100644 Group-Video/OpenVideoCall-Windows/Language/English/Source.def delete mode 100644 Group-Video/OpenVideoCall-Windows/Language/English/dllmain.cpp delete mode 100644 Group-Video/OpenVideoCall-Windows/Language/English/stdafx.cpp delete mode 100644 Group-Video/OpenVideoCall-Windows/Language/English/stdafx.h delete mode 100644 Group-Video/OpenVideoCall-Windows/Language/English/targetver.h create mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall.pro delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall.sln delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGButton.cpp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGButton.h delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGComboBox.cpp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGComboBox.h delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGConfig.cpp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGConfig.h delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGDesktopCaptureDlg.cpp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGDesktopCaptureDlg.h delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGEdit.cpp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGEdit.h delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGEngineEventHandler.cpp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGEngineEventHandler.h delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGEventDef.h delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGHyperLink.cpp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGHyperLink.h delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGLinkCtrl.cpp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGLinkCtrl.h delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGMessage.h delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGResourceVisitor.cpp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGResourceVisitor.h delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGScreenCaptureDlg.cpp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGScreenCaptureDlg.h delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGSliderCtrl.cpp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGSliderCtrl.h delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGVideoTestWnd.cpp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGVideoTestWnd.h delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGVideoWnd.cpp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGVideoWnd.h delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AgoraAudInputManager.cpp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AgoraAudInputManager.h delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AgoraCameraManager.cpp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AgoraCameraManager.h delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AgoraObject.cpp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AgoraObject.h delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AgoraPlayoutManager.cpp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/AgoraPlayoutManager.h delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/ChatDlg.cpp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/ChatDlg.h delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/DeviceDlg.cpp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/DeviceDlg.h delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/DskcapsetDlg.cpp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/DskcapsetDlg.h delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/EnterChannelDlg.cpp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/EnterChannelDlg.h delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/LanguageSet.cpp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/LanguageSet.h delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/LogoDlg.cpp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/LogoDlg.h delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/OpenVideoCall.cpp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/OpenVideoCall.h delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/OpenVideoCall.rc delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/OpenVideoCall.vcxproj delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/OpenVideoCall.vcxproj.filters delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/OpenVideoCall.vcxproj.user delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/OpenVideoCallDlg.cpp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/OpenVideoCallDlg.h delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/SetupDlg.cpp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/SetupDlg.h delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/VideoDlg.cpp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/VideoDlg.h delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BACKGROUND_VIDEO.bmp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNAUDIO_VIDEO.bmp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNCLOSE.bmp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNENDCALL_VIDEO.bmp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNFULLSCR_VIDEO.bmp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNMAUDIO_VIDEO.bmp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNMAX.bmp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNMIN.bmp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNMORE_VIDEO.bmp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNMSG_VIDEO.bmp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNNORSCR_VIDEO.bmp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNRESTORE.bmp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNSCRCAP_VIDEO.bmp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNSETUP_VIDEO.bmp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNTIP_VIDEO.bmp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNVIDEO_VIDEO.bmp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_CMBBTN.bmp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_CMBSEL.bmp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_DESKTOPSHARE_VIDEO.bmp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_DLG_LOGO.bmp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_DLG_MAIN.bmp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_LOGO.bmp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_MENU_DEVICE.bmp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_MENU_FILTER.bmp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_MENU_INFO.bmp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_MENU_MORE.bmp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_NETWORK_QUALITY.bmp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_SLD_HOVER.bmp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_SLD_NORMAL.bmp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/ID_TEST_AUDIO.wav delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/OpenVideoCall.ico delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/OpenVideoCall.rc2 delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/resource.h delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/stdafx.cpp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/stdafx.h delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/targetver.h delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/video_preprocessing_plugin.cpp delete mode 100644 Group-Video/OpenVideoCall-Windows/OpenVideoCall/video_preprocessing_plugin.h create mode 100644 Group-Video/OpenVideoCall-Windows/agoraconfig.cpp create mode 100644 Group-Video/OpenVideoCall-Windows/agoraconfig.h create mode 100644 Group-Video/OpenVideoCall-Windows/agoraobject.cpp create mode 100644 Group-Video/OpenVideoCall-Windows/agoraobject.h create mode 100644 Group-Video/OpenVideoCall-Windows/agorawindowmanager.cpp create mode 100644 Group-Video/OpenVideoCall-Windows/agorawindowmanager.h create mode 100644 Group-Video/OpenVideoCall-Windows/avdevice.cpp create mode 100644 Group-Video/OpenVideoCall-Windows/avdevice.h create mode 100644 Group-Video/OpenVideoCall-Windows/avdevice.ui create mode 100644 Group-Video/OpenVideoCall-Windows/build_release.bat create mode 100644 Group-Video/OpenVideoCall-Windows/enterroom.cpp create mode 100644 Group-Video/OpenVideoCall-Windows/enterroom.h create mode 100644 Group-Video/OpenVideoCall-Windows/enterroom.ui create mode 100644 Group-Video/OpenVideoCall-Windows/inroom.cpp create mode 100644 Group-Video/OpenVideoCall-Windows/inroom.h create mode 100644 Group-Video/OpenVideoCall-Windows/inroom.ui create mode 100644 Group-Video/OpenVideoCall-Windows/inroomdig.cpp create mode 100644 Group-Video/OpenVideoCall-Windows/inroomdig.h create mode 100644 Group-Video/OpenVideoCall-Windows/inroomdig.ui create mode 100644 Group-Video/OpenVideoCall-Windows/main.cpp create mode 100644 Group-Video/OpenVideoCall-Windows/nettestdetail.cpp create mode 100644 Group-Video/OpenVideoCall-Windows/nettestdetail.h create mode 100644 Group-Video/OpenVideoCall-Windows/nettestdetail.ui create mode 100644 Group-Video/OpenVideoCall-Windows/nettesting.cpp create mode 100644 Group-Video/OpenVideoCall-Windows/nettesting.h create mode 100644 Group-Video/OpenVideoCall-Windows/nettesting.ui create mode 100644 Group-Video/OpenVideoCall-Windows/nettestresult.cpp create mode 100644 Group-Video/OpenVideoCall-Windows/nettestresult.h create mode 100644 Group-Video/OpenVideoCall-Windows/nettestresult.ui create mode 100644 Group-Video/OpenVideoCall-Windows/openvideocall.cpp create mode 100644 Group-Video/OpenVideoCall-Windows/openvideocall.h create mode 100644 Group-Video/OpenVideoCall-Windows/openvideocall.ico create mode 100644 Group-Video/OpenVideoCall-Windows/openvideocall.qrc create mode 100644 Group-Video/OpenVideoCall-Windows/openvideocall.rc create mode 100644 Group-Video/OpenVideoCall-Windows/openvideocall.ui create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/OVC-win-03.jpg create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/OVC-win-config.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/OVC-win-home.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/OVC-win-more users.jpg create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/OVC-win-netdetail.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/OVC-win-netresult.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/OVC-win-nettest.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/allmute remote.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/allmute.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/box-01.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/dropdow-01.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/dropdown-02.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/dropdown-03.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/edit.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/edit1.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/edit2.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/edit3.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/edit4.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/edit5.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/gray.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/icon-back hover.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/icon-back.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/icon-camera off.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/icon-camera on.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/icon-camera.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/icon-close default.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/icon-close hover.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/icon-hang up hover.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/icon-hang up.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/icon-loading.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/icon-micorophone off.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/icon-micorophone on.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/icon-micorophone.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/icon-min default.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/icon-min hover.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/icon-setting hover.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/icon-setting.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/loading.gif create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/mutevideo remote.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/mutevideo.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/pic-bad.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/pic-good.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/pic-poor.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/qlabel.h create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/slider.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/switch-off.png create mode 100644 Group-Video/OpenVideoCall-Windows/uiresource/switch-open.png create mode 100755 Group-Video/OpenVideoCall-iOS-Objective-C/clear.sh create mode 100644 Group-Video/OpenVideoCall-iOS/OpenVideoCall/AGEVideoLayout/AGEEventsObserver.swift create mode 100644 Group-Video/OpenVideoCall-iOS/OpenVideoCall/AGEVideoLayout/AGEVideoConstraints.swift create mode 100644 Group-Video/OpenVideoCall-iOS/OpenVideoCall/AGEVideoLayout/AGEVideoContainer.swift create mode 100644 Group-Video/OpenVideoCall-iOS/OpenVideoCall/AGEVideoLayout/AGEVideoLayout.swift rename Group-Video/{OpenVideoCall-macOS/OpenVideoCall => OpenVideoCall-iOS/OpenVideoCall/AGEVideoLayout}/AGEView.swift (67%) delete mode 100644 Group-Video/OpenVideoCall-iOS/OpenVideoCall/ActivityViewController.swift rename Group-Video/OpenVideoCall-iOS/OpenVideoCall/{MediaInfo.swift => AgoraExtension.swift} (51%) delete mode 100644 Group-Video/OpenVideoCall-iOS/OpenVideoCall/OpenVideoCall-Bridging-Header.h create mode 100755 Group-Video/OpenVideoCall-iOS/OpenVideoCall/StatisticsInfo.swift delete mode 100644 Group-Video/OpenVideoCall-iOS/OpenVideoCall/VideoViewLayouter.swift create mode 100755 Group-Video/OpenVideoCall-iOS/clear.sh delete mode 100644 Group-Video/OpenVideoCall-macOS/OpenVideoCall/AGEVideoContainer.swift delete mode 100644 Group-Video/OpenVideoCall-macOS/OpenVideoCall/AGEVideoLayout.swift create mode 100644 Group-Video/OpenVideoCall-macOS/OpenVideoCall/AGEVideoLayout/AGEEventsObserver.swift create mode 100644 Group-Video/OpenVideoCall-macOS/OpenVideoCall/AGEVideoLayout/AGEVideoConstraints.swift create mode 100644 Group-Video/OpenVideoCall-macOS/OpenVideoCall/AGEVideoLayout/AGEVideoContainer.swift create mode 100644 Group-Video/OpenVideoCall-macOS/OpenVideoCall/AGEVideoLayout/AGEVideoLayout.swift create mode 100644 Group-Video/OpenVideoCall-macOS/OpenVideoCall/AGEVideoLayout/AGEView.swift create mode 100755 Group-Video/OpenVideoCall-macOS/clear.sh delete mode 100755 LICENSE.md delete mode 100644 One-to-One-Video/Agora-Android-Tutorial-1to1/README.yaml delete mode 100644 One-to-One-Video/Agora-Android-Tutorial-1to1/README.zh.yaml delete mode 100644 One-to-One-Video/Agora-Android-Tutorial-Kotlin-1to1/README.yaml delete mode 100644 One-to-One-Video/Agora-Android-Tutorial-Kotlin-1to1/README.zh.yaml delete mode 100644 One-to-One-Video/Agora-Web-Tutorial-1to1-Webpack/README.yaml delete mode 100644 One-to-One-Video/Agora-Web-Tutorial-1to1-Webpack/README.zh.yaml delete mode 100644 One-to-One-Video/Agora-Web-Tutorial-1to1/README.yaml delete mode 100644 One-to-One-Video/Agora-Web-Tutorial-1to1/README.zh.yaml delete mode 100755 One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/Agora iOS Tutorial Objective-C.xcodeproj/project.xcworkspace/contents.xcworkspacedata rename One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/{Agora iOS Tutorial Objective-C.xcodeproj => Agora-iOS-Tutorial-Objective-C.xcodeproj}/.xcodesamplecode.plist (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/{Agora iOS Tutorial Objective-C.xcodeproj => Agora-iOS-Tutorial-Objective-C.xcodeproj}/project.pbxproj (67%) create mode 100755 One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/Agora-iOS-Tutorial-Objective-C.xcodeproj/project.xcworkspace/contents.xcworkspacedata rename One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/{Agora iOS Tutorial Objective-C.xcodeproj => Agora-iOS-Tutorial-Objective-C.xcodeproj}/project.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist (100%) create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/Agora-iOS-Tutorial-Objective-C.xcodeproj/xcshareddata/xcschemes/Agora-iOS-Tutorial-Objective-C.xcscheme rename One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/{Agora iOS Tutorial Objective-C => Agora-iOS-Tutorial-Objective-C}/AppDelegate.h (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/{Agora iOS Tutorial Objective-C => Agora-iOS-Tutorial-Objective-C}/AppDelegate.m (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/{Agora iOS Tutorial Objective-C/VideoChat => Agora-iOS-Tutorial-Objective-C}/AppID.h (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/{Agora iOS Tutorial Objective-C/VideoChat => Agora-iOS-Tutorial-Objective-C}/AppID.m (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/{Agora iOS Tutorial Objective-C => Agora-iOS-Tutorial-Objective-C}/Assets.xcassets/AppIcon.appiconset/Contents.json (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/{Agora iOS Tutorial Objective-C => Agora-iOS-Tutorial-Objective-C}/Assets.xcassets/Contents.json (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/{Agora iOS Tutorial Objective-C => Agora-iOS-Tutorial-Objective-C}/Assets.xcassets/hangUpButton.imageset/Contents.json (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/{Agora iOS Tutorial Objective-C => Agora-iOS-Tutorial-Objective-C}/Assets.xcassets/hangUpButton.imageset/hangup.png (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/{Agora iOS Tutorial Objective-C => Agora-iOS-Tutorial-Objective-C}/Assets.xcassets/localVideoMutedBg.imageset/Contents.json (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/{Agora iOS Tutorial Objective-C => Agora-iOS-Tutorial-Objective-C}/Assets.xcassets/localVideoMutedBg.imageset/cameramute.png (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/{Agora iOS Tutorial Objective-C => Agora-iOS-Tutorial-Objective-C}/Assets.xcassets/muteButton.imageset/Contents.json (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/{Agora iOS Tutorial Objective-C => Agora-iOS-Tutorial-Objective-C}/Assets.xcassets/muteButton.imageset/mute.png (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/{Agora iOS Tutorial Objective-C => Agora-iOS-Tutorial-Objective-C}/Assets.xcassets/muteButtonSelected.imageset/Contents.json (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/{Agora iOS Tutorial Objective-C => Agora-iOS-Tutorial-Objective-C}/Assets.xcassets/muteButtonSelected.imageset/unmute.png (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/{Agora iOS Tutorial Objective-C => Agora-iOS-Tutorial-Objective-C}/Assets.xcassets/switchCameraButton.imageset/Contents.json (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/{Agora iOS Tutorial Objective-C => Agora-iOS-Tutorial-Objective-C}/Assets.xcassets/switchCameraButton.imageset/switch_camera.png (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/{Agora iOS Tutorial Objective-C => Agora-iOS-Tutorial-Objective-C}/Assets.xcassets/switchCameraButtonSelected.imageset/Contents.json (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/{Agora iOS Tutorial Objective-C => Agora-iOS-Tutorial-Objective-C}/Assets.xcassets/switchCameraButtonSelected.imageset/unswitch-camera.png (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/{Agora iOS Tutorial Objective-C => Agora-iOS-Tutorial-Objective-C}/Assets.xcassets/videoMuteButton.imageset/Contents.json (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/{Agora iOS Tutorial Objective-C => Agora-iOS-Tutorial-Objective-C}/Assets.xcassets/videoMuteButton.imageset/cameraoff.png (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/{Agora iOS Tutorial Objective-C => Agora-iOS-Tutorial-Objective-C}/Assets.xcassets/videoMuteButtonSelected.imageset/Contents.json (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/{Agora iOS Tutorial Objective-C => Agora-iOS-Tutorial-Objective-C}/Assets.xcassets/videoMuteButtonSelected.imageset/cameraoff copy.png (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/{Agora iOS Tutorial Objective-C => Agora-iOS-Tutorial-Objective-C}/Assets.xcassets/videoMutedIndicator.imageset/Contents.json (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/{Agora iOS Tutorial Objective-C => Agora-iOS-Tutorial-Objective-C}/Assets.xcassets/videoMutedIndicator.imageset/cameraoff_mainVideo.png (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/{Agora iOS Tutorial Objective-C => Agora-iOS-Tutorial-Objective-C}/Base.lproj/LaunchScreen.storyboard (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/{Agora iOS Tutorial Objective-C => Agora-iOS-Tutorial-Objective-C}/Base.lproj/Main.storyboard (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/{Agora iOS Tutorial Objective-C => Agora-iOS-Tutorial-Objective-C}/Info.plist (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/{Agora iOS Tutorial Objective-C/VideoChat => Agora-iOS-Tutorial-Objective-C}/VideoChatViewController.h (86%) rename One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/{Agora iOS Tutorial Objective-C/VideoChat => Agora-iOS-Tutorial-Objective-C}/VideoChatViewController.m (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/{Agora iOS Tutorial Objective-C => Agora-iOS-Tutorial-Objective-C}/main.m (100%) create mode 100755 One-to-One-Video/Agora-iOS-Tutorial-Objective-C-1to1/clear.sh delete mode 100755 One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/Agora iOS Tutorial.xcodeproj/project.xcworkspace/contents.xcworkspacedata rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial.xcodeproj => Agora-iOS-Tutorial.xcodeproj}/.xcodesamplecode.plist (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial.xcodeproj => Agora-iOS-Tutorial.xcodeproj}/project.pbxproj (71%) create mode 100755 One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/Agora-iOS-Tutorial.xcodeproj/project.xcworkspace/contents.xcworkspacedata rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial.xcodeproj => Agora-iOS-Tutorial.xcodeproj}/project.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial.xcodeproj/xcshareddata/xcschemes/Agora iOS Tutorial.xcscheme => Agora-iOS-Tutorial.xcodeproj/xcshareddata/xcschemes/Agora-iOS-Tutorial.xcscheme} (77%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/AppDelegate.swift (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/AppID.swift (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Assets.xcassets/AppIcon.appiconset/Contents.json (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Assets.xcassets/Contents.json (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Assets.xcassets/big_logo.imageset/B8D9B541-3C15-4F3F-B817-1BFA03224F58@1x.png (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Assets.xcassets/big_logo.imageset/B8D9B541-3C15-4F3F-B817-1BFA03224F58@2x.png (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Assets.xcassets/big_logo.imageset/B8D9B541-3C15-4F3F-B817-1BFA03224F58@3x.png (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Assets.xcassets/big_logo.imageset/Contents.json (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Assets.xcassets/call.imageset/Contents.json (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Assets.xcassets/call.imageset/call@4x.png (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Assets.xcassets/call_pressed.imageset/Contents.json (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Assets.xcassets/call_pressed.imageset/call_pressed@4x.png (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Assets.xcassets/end.imageset/Contents.json (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Assets.xcassets/end.imageset/end@4x.png (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Assets.xcassets/end_pressed.imageset/Contents.json (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Assets.xcassets/end_pressed.imageset/end_pressed@4x.png (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Assets.xcassets/gray_bg.imageset/Contents.json (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Assets.xcassets/gray_bg.imageset/gray_bg@1x.png (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Assets.xcassets/gray_bg.imageset/gray_bg@2x.png (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Assets.xcassets/gray_bg.imageset/gray_bg@3x.png (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Assets.xcassets/logo.imageset/8A1BE415-1E76-4F1B-AD85-3C21C4E0DCDE@1x.png (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Assets.xcassets/logo.imageset/8A1BE415-1E76-4F1B-AD85-3C21C4E0DCDE@2x.png (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Assets.xcassets/logo.imageset/8A1BE415-1E76-4F1B-AD85-3C21C4E0DCDE@3x.png (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Assets.xcassets/logo.imageset/Contents.json (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Assets.xcassets/mic.imageset/Contents.json (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Assets.xcassets/mic.imageset/mic@4x.png (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Assets.xcassets/mic_pressed.imageset/Contents.json (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Assets.xcassets/mic_pressed.imageset/mic_pressed@4x.png (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Assets.xcassets/mute.imageset/Contents.json (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Assets.xcassets/mute.imageset/mute@4x.png (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Assets.xcassets/mute_pressed.imageset/Contents.json (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Assets.xcassets/mute_pressed.imageset/mute_pressed@4x.png (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Assets.xcassets/switch.imageset/Contents.json (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Assets.xcassets/switch.imageset/switch@4x.png (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Assets.xcassets/switch_pressed.imageset/Contents.json (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Assets.xcassets/switch_pressed.imageset/switch_pressed@4x.png (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Base.lproj/LaunchScreen.storyboard (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Base.lproj/Main.storyboard (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Info.plist (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/Log.storyboard (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/LogViewController.swift (100%) rename One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/{Agora iOS Tutorial => Agora-iOS-Tutorial}/VideoChatViewController.swift (99%) create mode 100755 One-to-One-Video/Agora-iOS-Tutorial-Swift-1to1/clear.sh create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/.gitignore rename One-to-One-Video/{Agora-macOS-Tutorial-Objective-C-1to1/Agora Mac Tutorial Objective-C.xcodeproj => Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1.xcodeproj}/.xcodesamplecode.plist (100%) create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1.xcodeproj/project.pbxproj create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1/AppDelegate.swift create mode 100755 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1/AppID.swift create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1/Assets.xcassets/AppIcon.appiconset/Contents.json rename One-to-One-Video/{Agora-macOS-Tutorial-Objective-C-1to1/Agora Mac Tutorial Objective-C => Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1}/Assets.xcassets/Contents.json (100%) mode change 100755 => 100644 create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1/Assets.xcassets/big_logo.imageset/Contents.json create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1/Assets.xcassets/big_logo.imageset/big_logo.png create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1/Assets.xcassets/big_logo.imageset/big_logo@2x.png create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1/Assets.xcassets/big_logo.imageset/big_logo@3x.png create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1/Assets.xcassets/call.imageset/Contents.json create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1/Assets.xcassets/call.imageset/call@4x.png create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1/Assets.xcassets/end.imageset/Contents.json create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1/Assets.xcassets/end.imageset/end@4x.png create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1/Assets.xcassets/localBackColor.colorset/Contents.json create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1/Assets.xcassets/logErrorColor.colorset/Contents.json create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1/Assets.xcassets/logInfoColor.colorset/Contents.json create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1/Assets.xcassets/logWarningColor.colorset/Contents.json create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1/Assets.xcassets/logo.imageset/Contents.json create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1/Assets.xcassets/logo.imageset/logo@1x.png create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1/Assets.xcassets/logo.imageset/logo@2x.png create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1/Assets.xcassets/logo.imageset/logo@3x.png create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1/Assets.xcassets/mic.imageset/Contents.json create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1/Assets.xcassets/mic.imageset/mic@4x.png create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1/Assets.xcassets/mute.imageset/Contents.json create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1/Assets.xcassets/mute.imageset/mute@4x.png create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1/Assets.xcassets/remoteBackColor.colorset/Contents.json create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1/Assets.xcassets/switch.imageset/Contents.json create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1/Assets.xcassets/switch.imageset/switch@4x.png create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1/Base.lproj/LaunchScreen.storyboard create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1/ContentView.swift create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1/Info.plist rename One-to-One-Video/{Agora-macOS-Tutorial-Swift-1to1/Agora Mac Tutorial Swift/Assets.xcassets => Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1/Preview Content/Preview Assets.xcassets}/Contents.json (100%) mode change 100755 => 100644 create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1/SceneDelegate.swift create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1/VideoCanvas.swift create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1/VideoEngine.swift create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/Agora-iOS-Tutorial-SwiftUI-1to1/VideoSessionView.swift create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/README.md create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/README.zh.md create mode 100755 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/build.sh create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/ci.env.py create mode 100755 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/clear.sh create mode 100644 One-to-One-Video/Agora-iOS-Tutorial-SwiftUI-1to1/exportPlist.plist delete mode 100755 One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/Agora Mac Tutorial Objective-C.xcodeproj/project.xcworkspace/contents.xcworkspacedata rename One-to-One-Video/{Agora-macOS-Tutorial-Swift-1to1/Agora Mac Tutorial Swift.xcodeproj => Agora-macOS-Tutorial-Objective-C-1to1/Agora-Mac-Tutorial-Objective-C.xcodeproj}/.xcodesamplecode.plist (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/{Agora Mac Tutorial Objective-C.xcodeproj => Agora-Mac-Tutorial-Objective-C.xcodeproj}/project.pbxproj (73%) create mode 100755 One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/Agora-Mac-Tutorial-Objective-C.xcodeproj/project.xcworkspace/contents.xcworkspacedata rename One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/{Agora Mac Tutorial Objective-C.xcodeproj => Agora-Mac-Tutorial-Objective-C.xcodeproj}/project.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist (100%) create mode 100644 One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/Agora-Mac-Tutorial-Objective-C.xcodeproj/xcshareddata/xcschemes/Agora-Mac-Tutorial-Objective-C.xcscheme rename One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/{Agora Mac Tutorial Objective-C => Agora-Mac-Tutorial-Objective-C}/AppDelegate.h (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/{Agora Mac Tutorial Objective-C => Agora-Mac-Tutorial-Objective-C}/AppDelegate.m (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/{Agora Mac Tutorial Objective-C/VideoChat => Agora-Mac-Tutorial-Objective-C}/AppID.h (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/{Agora Mac Tutorial Objective-C/VideoChat => Agora-Mac-Tutorial-Objective-C}/AppID.m (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/{Agora Mac Tutorial Objective-C => Agora-Mac-Tutorial-Objective-C}/Assets.xcassets/AppIcon.appiconset/Contents.json (100%) create mode 100755 One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/Agora-Mac-Tutorial-Objective-C/Assets.xcassets/Contents.json rename One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/{Agora Mac Tutorial Objective-C => Agora-Mac-Tutorial-Objective-C}/Assets.xcassets/deviceSelectionButton.imageset/Contents.json (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/{Agora Mac Tutorial Objective-C => Agora-Mac-Tutorial-Objective-C}/Assets.xcassets/deviceSelectionButton.imageset/device_selection.png (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/{Agora Mac Tutorial Objective-C => Agora-Mac-Tutorial-Objective-C}/Assets.xcassets/hangUpButton.imageset/Contents.json (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/{Agora Mac Tutorial Objective-C => Agora-Mac-Tutorial-Objective-C}/Assets.xcassets/hangUpButton.imageset/hangup.png (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/{Agora Mac Tutorial Objective-C => Agora-Mac-Tutorial-Objective-C}/Assets.xcassets/localVideoMutedBg.imageset/Contents.json (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/{Agora Mac Tutorial Objective-C => Agora-Mac-Tutorial-Objective-C}/Assets.xcassets/localVideoMutedBg.imageset/cameramutehorizontal.png (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/{Agora Mac Tutorial Objective-C => Agora-Mac-Tutorial-Objective-C}/Assets.xcassets/muteButton.imageset/Contents.json (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/{Agora Mac Tutorial Objective-C => Agora-Mac-Tutorial-Objective-C}/Assets.xcassets/muteButton.imageset/mute.png (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/{Agora Mac Tutorial Objective-C => Agora-Mac-Tutorial-Objective-C}/Assets.xcassets/muteButtonSelected.imageset/Contents.json (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/{Agora Mac Tutorial Objective-C => Agora-Mac-Tutorial-Objective-C}/Assets.xcassets/muteButtonSelected.imageset/unmute.png (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/{Agora Mac Tutorial Objective-C => Agora-Mac-Tutorial-Objective-C}/Assets.xcassets/screenShareButton.imageset/Contents.json (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/{Agora Mac Tutorial Objective-C => Agora-Mac-Tutorial-Objective-C}/Assets.xcassets/screenShareButton.imageset/screen_sharing.png (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/{Agora Mac Tutorial Objective-C => Agora-Mac-Tutorial-Objective-C}/Assets.xcassets/screenShareButtonSelected.imageset/Contents.json (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/{Agora Mac Tutorial Objective-C => Agora-Mac-Tutorial-Objective-C}/Assets.xcassets/screenShareButtonSelected.imageset/unscreen_share.png (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/{Agora Mac Tutorial Objective-C => Agora-Mac-Tutorial-Objective-C}/Assets.xcassets/videoMuteButton.imageset/Contents.json (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/{Agora Mac Tutorial Objective-C => Agora-Mac-Tutorial-Objective-C}/Assets.xcassets/videoMuteButton.imageset/cameraoff.png (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/{Agora Mac Tutorial Objective-C => Agora-Mac-Tutorial-Objective-C}/Assets.xcassets/videoMuteButtonSelected.imageset/Contents.json (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/{Agora Mac Tutorial Objective-C => Agora-Mac-Tutorial-Objective-C}/Assets.xcassets/videoMuteButtonSelected.imageset/cameraon.png (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/{Agora Mac Tutorial Objective-C => Agora-Mac-Tutorial-Objective-C}/Assets.xcassets/videoMutedIndicator.imageset/Contents.json (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/{Agora Mac Tutorial Objective-C => Agora-Mac-Tutorial-Objective-C}/Assets.xcassets/videoMutedIndicator.imageset/cameraoff_mainVideo.png (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/{Agora Mac Tutorial Objective-C => Agora-Mac-Tutorial-Objective-C}/Base.lproj/Main.storyboard (95%) rename One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/{Agora Mac Tutorial Objective-C/VideoChat => Agora-Mac-Tutorial-Objective-C}/DeviceSelectionViewController.h (87%) rename One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/{Agora Mac Tutorial Objective-C/VideoChat => Agora-Mac-Tutorial-Objective-C}/DeviceSelectionViewController.m (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/{Agora Mac Tutorial Objective-C => Agora-Mac-Tutorial-Objective-C}/Info.plist (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/{Agora Mac Tutorial Objective-C/VideoChat => Agora-Mac-Tutorial-Objective-C}/VideoChatViewController.h (87%) rename One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/{Agora Mac Tutorial Objective-C/VideoChat => Agora-Mac-Tutorial-Objective-C}/VideoChatViewController.m (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/{Agora Mac Tutorial Objective-C => Agora-Mac-Tutorial-Objective-C}/main.m (100%) create mode 100755 One-to-One-Video/Agora-macOS-Tutorial-Objective-C-1to1/clear.sh delete mode 100755 One-to-One-Video/Agora-macOS-Tutorial-Swift-1to1/Agora Mac Tutorial Swift.xcodeproj/project.xcworkspace/contents.xcworkspacedata create mode 100644 One-to-One-Video/Agora-macOS-Tutorial-Swift-1to1/Agora-Mac-Tutorial-Swift.xcodeproj/.xcodesamplecode.plist rename One-to-One-Video/Agora-macOS-Tutorial-Swift-1to1/{Agora Mac Tutorial Swift.xcodeproj => Agora-Mac-Tutorial-Swift.xcodeproj}/project.pbxproj (74%) create mode 100755 One-to-One-Video/Agora-macOS-Tutorial-Swift-1to1/Agora-Mac-Tutorial-Swift.xcodeproj/project.xcworkspace/contents.xcworkspacedata rename One-to-One-Video/Agora-macOS-Tutorial-Swift-1to1/{Agora Mac Tutorial Swift.xcodeproj => Agora-Mac-Tutorial-Swift.xcodeproj}/project.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist (100%) create mode 100644 One-to-One-Video/Agora-macOS-Tutorial-Swift-1to1/Agora-Mac-Tutorial-Swift.xcodeproj/xcshareddata/xcschemes/Agora-Mac-Tutorial-Swift.xcscheme rename One-to-One-Video/Agora-macOS-Tutorial-Swift-1to1/{Agora Mac Tutorial Swift => Agora-Mac-Tutorial-Swift}/AppDelegate.swift (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Swift-1to1/{Agora Mac Tutorial Swift/VideoChat => Agora-Mac-Tutorial-Swift}/AppID.swift (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Swift-1to1/{Agora Mac Tutorial Swift => Agora-Mac-Tutorial-Swift}/Assets.xcassets/AppIcon.appiconset/Contents.json (100%) create mode 100755 One-to-One-Video/Agora-macOS-Tutorial-Swift-1to1/Agora-Mac-Tutorial-Swift/Assets.xcassets/Contents.json rename One-to-One-Video/Agora-macOS-Tutorial-Swift-1to1/{Agora Mac Tutorial Swift => Agora-Mac-Tutorial-Swift}/Assets.xcassets/deviceSelectionButton.imageset/Contents.json (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Swift-1to1/{Agora Mac Tutorial Swift => Agora-Mac-Tutorial-Swift}/Assets.xcassets/deviceSelectionButton.imageset/device_selection.png (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Swift-1to1/{Agora Mac Tutorial Swift => Agora-Mac-Tutorial-Swift}/Assets.xcassets/hangUpButton.imageset/Contents.json (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Swift-1to1/{Agora Mac Tutorial Swift => Agora-Mac-Tutorial-Swift}/Assets.xcassets/hangUpButton.imageset/hangup.png (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Swift-1to1/{Agora Mac Tutorial Swift => Agora-Mac-Tutorial-Swift}/Assets.xcassets/localVideoMutedBg.imageset/Contents.json (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Swift-1to1/{Agora Mac Tutorial Swift => Agora-Mac-Tutorial-Swift}/Assets.xcassets/localVideoMutedBg.imageset/cameramutehorizontal.png (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Swift-1to1/{Agora Mac Tutorial Swift => Agora-Mac-Tutorial-Swift}/Assets.xcassets/muteButton.imageset/Contents.json (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Swift-1to1/{Agora Mac Tutorial Swift => Agora-Mac-Tutorial-Swift}/Assets.xcassets/muteButton.imageset/mute.png (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Swift-1to1/{Agora Mac Tutorial Swift => Agora-Mac-Tutorial-Swift}/Assets.xcassets/muteButtonSelected.imageset/Contents.json (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Swift-1to1/{Agora Mac Tutorial Swift => Agora-Mac-Tutorial-Swift}/Assets.xcassets/muteButtonSelected.imageset/unmute.png (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Swift-1to1/{Agora Mac Tutorial Swift => Agora-Mac-Tutorial-Swift}/Assets.xcassets/screenShareButton.imageset/Contents.json (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Swift-1to1/{Agora Mac Tutorial Swift => Agora-Mac-Tutorial-Swift}/Assets.xcassets/screenShareButton.imageset/screen_sharing.png (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Swift-1to1/{Agora Mac Tutorial Swift => Agora-Mac-Tutorial-Swift}/Assets.xcassets/screenShareButtonSelected.imageset/Contents.json (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Swift-1to1/{Agora Mac Tutorial Swift => Agora-Mac-Tutorial-Swift}/Assets.xcassets/screenShareButtonSelected.imageset/unscreen_share.png (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Swift-1to1/{Agora Mac Tutorial Swift => Agora-Mac-Tutorial-Swift}/Assets.xcassets/videoMuteButton.imageset/Contents.json (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Swift-1to1/{Agora Mac Tutorial Swift => Agora-Mac-Tutorial-Swift}/Assets.xcassets/videoMuteButton.imageset/cameraoff.png (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Swift-1to1/{Agora Mac Tutorial Swift => Agora-Mac-Tutorial-Swift}/Assets.xcassets/videoMuteButtonSelected.imageset/Contents.json (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Swift-1to1/{Agora Mac Tutorial Swift => Agora-Mac-Tutorial-Swift}/Assets.xcassets/videoMuteButtonSelected.imageset/cameraon.png (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Swift-1to1/{Agora Mac Tutorial Swift => Agora-Mac-Tutorial-Swift}/Assets.xcassets/videoMutedIndicator.imageset/Contents.json (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Swift-1to1/{Agora Mac Tutorial Swift => Agora-Mac-Tutorial-Swift}/Assets.xcassets/videoMutedIndicator.imageset/cameraoff_mainVideo.png (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Swift-1to1/{Agora Mac Tutorial Swift => Agora-Mac-Tutorial-Swift}/Base.lproj/Main.storyboard (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Swift-1to1/{Agora Mac Tutorial Swift/VideoChat => Agora-Mac-Tutorial-Swift}/DeviceSelectionViewController.swift (99%) rename One-to-One-Video/Agora-macOS-Tutorial-Swift-1to1/{Agora Mac Tutorial Swift => Agora-Mac-Tutorial-Swift}/Info.plist (100%) rename One-to-One-Video/Agora-macOS-Tutorial-Swift-1to1/{Agora Mac Tutorial Swift/VideoChat => Agora-Mac-Tutorial-Swift}/VideoChatViewController.swift (99%) create mode 100755 One-to-One-Video/Agora-macOS-Tutorial-Swift-1to1/clear.sh delete mode 100644 README.md create mode 100755 cicd/scripts/sdkdownload.sh delete mode 100755 gen_readme.sh delete mode 100755 gen_readme_all.sh diff --git a/Group-Video/OpenVideoCall-Android/.gitignore b/Group-Video/OpenVideoCall-Android/.gitignore index 00b607ce..7b6c0341 100644 --- a/Group-Video/OpenVideoCall-Android/.gitignore +++ b/Group-Video/OpenVideoCall-Android/.gitignore @@ -1,3 +1,8 @@ +include +agora-rtc-sdk.jar +*.so +.settings + # built application files *.apk *.ap_ diff --git a/Group-Video/OpenVideoCall-Android/README.md b/Group-Video/OpenVideoCall-Android/README.md index cc9ecf73..a9c8f2e7 100755 --- a/Group-Video/OpenVideoCall-Android/README.md +++ b/Group-Video/OpenVideoCall-Android/README.md @@ -9,10 +9,9 @@ With this sample app, you can: - Mute / unmute audio - Enable / disable video - Switch camera -- Send message to channel - Setup resolution, frame rate and bit rate - Enable encryption -- Enable / disable black and white filter +- Enable beautify filter ## Prerequisites @@ -53,7 +52,7 @@ The SDK must be integrated into the sample project before it can opened and buil ... dependencies { ... - implementation 'io.agora.rtc:full-sdk:2.4.1' + implementation 'io.agora.rtc:full-sdk:3.0.0' } ``` @@ -81,8 +80,13 @@ Or use `Gradle` to build and run. ## Resources -- You can find full API document at [Document Center](https://docs.agora.io/en/) -- You can file bugs about this demo at [issue](https://github.com/AgoraIO/Basic-Video-Call/issues) +- For potential issues, take a look at our [FAQ](https://docs.agora.io/cn/faq) first +- Dive into [Agora SDK Samples](https://github.com/AgoraIO) to see more tutorials +- Take a look at [Agora Use Case](https://github.com/AgoraIO-usecase) for more complicated real use case +- Repositories managed by developer communities can be found at [Agora Community](https://github.com/AgoraIO-Community) +- You can find full API documentation at [Document Center](https://docs.agora.io/en/) +- If you encounter problems during integration, you can ask question in [Stack Overflow](https://stackoverflow.com/questions/tagged/agora.io) +- You can file bugs about this sample at [issue](https://github.com/AgoraIO/Basic-Video-Call/issues) ## License diff --git a/Group-Video/OpenVideoCall-Android/README.yaml b/Group-Video/OpenVideoCall-Android/README.yaml deleted file mode 100644 index 072d434e..00000000 --- a/Group-Video/OpenVideoCall-Android/README.yaml +++ /dev/null @@ -1,52 +0,0 @@ -Meta: - name: Open Video Call for Android - # en or cn - lang: en - version: 2.4.1 - # | 代表这里是字符串 - description: | - The Open Video Call for Android Sample App is an open-source demo that will help you get video chat integrated directly into your Android applications using the Agora Video SDK. - - With this sample app, you can: - - Join / leave channel - - Mute / unmute audio - - Enable / disable video - - Switch camera - - Send message to channel - - Setup resolution, frame rate and bit rate - - Enable encryption - - Enable / disable black and white filter - -Prerequisites: - - Android Studio 3.3 or above - - Real devices (Nexus 5X or other devices) - - Some simulators are function missing or have performance issue, so real device is the best choice - -QuickStart: - description: - This section shows you how to prepare, build, and run the sample application. - sections: - - title: Obtain an App ID - content: | - $_{APPID} - 5. Update "app/src/main/res/values/strings_config.xml" with your App ID and Token. - ``` - <#YOUR APP ID#> - - - <#YOUR TOKEN#> - ``` - - title: Integrate the Agora Video SDK - content: | - $_{ANDROID_INTEGRATE} - - - title: Run the Application - content: | - $_{ANDROID_RUN} - -Resources: - document: https://docs.agora.io/en/ - issue: https://github.com/AgoraIO/Basic-Video-Call/issues - -License: - type: MIT \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Android/README.zh.md b/Group-Video/OpenVideoCall-Android/README.zh.md index 2baf4d15..259db1af 100644 --- a/Group-Video/OpenVideoCall-Android/README.zh.md +++ b/Group-Video/OpenVideoCall-Android/README.zh.md @@ -10,12 +10,9 @@ - 静音和解除静音; - 关闭摄像头和打开摄像头; - 切换前置摄像头和后置摄像头; -- 发送频道内消息; - 选择分辨率、码率和帧率; - 设置加密模式; -- 开启和关闭黑白滤镜; - -你也可以在这里查看入门版的示例项目:[Agora-Android-Tutorial-1to1](https://github.com/AgoraIO/Basic-Video-Call/tree/master/One-to-One-Video/Agora-Android-Tutorial-1to1) +- 开启和关闭基础美颜; ## 环境准备 @@ -46,14 +43,12 @@ ### 集成 Agora 视频 SDK 集成方式有以下两种: - - 首选集成方式: + - 通过JCenter集成: - 在项目对应的模块的 `app/build.gradle` 文件的依赖属性中加入通过 JCenter 自动集成 Agora 视频 SDK 的地址: ``` - implementation 'io.agora.rtc:full-sdk:2.4.1' + implementation 'io.agora.rtc:full-sdk:3.0.0' ``` - (如果要在自己的应用中集成 Agora 视频 SDK,添加链接地址是最重要的一步。) - - 在 [Agora.io SDK](https://www.agora.io/cn/download/) 下载 **视频通话 + 直播 SDK**,解压后将其中的 **libs**/**include** 文件夹下的 ***.h** 复制到本项目的 **app**/**src**/**main**/**cpp**/**agora** 下。 - - 次选集成方式: + - 手动集成: - 在 [Agora.io SDK](https://www.agora.io/cn/download/) 下载 **视频通话 + 直播 SDK**并解压,按以下对应关系将 **libs** 目录的内容复制到项目内。 SDK目录|项目目录 @@ -62,6 +57,7 @@ **arm64-v8a** folder|**/app/src/main/jniLibs** folder **x86** folder|**/app/src/main/jniLibs** folder **armeabi-v7a** folder|**/app/src/main/jniLibs** folder + - 若需要需要使用C++头文件,可以在解压SDK后将其中的 **libs**/**include** 文件夹下的 ***.h** 复制到本项目的 **app**/**src**/**main**/**cpp**/**agora** 下。 ### 启动应用程序 @@ -73,11 +69,13 @@ ## 联系我们 +- 如果你遇到了困难,可以先参阅[常见问题](https://docs.agora.io/cn/faq) +- 如果你想了解更多官方示例,可以参考[官方SDK示例](https://github.com/AgoraIO) +- 如果你想了解声网SDK在复杂场景下的应用,可以参考[官方场景案例](https://github.com/AgoraIO-usecase) +- 如果你想了解声网的一些社区开发者维护的项目,可以查看[社区](https://github.com/AgoraIO-Community) - 完整的 API 文档见 [文档中心](https://docs.agora.io/cn/) -- 如果在集成中遇到问题, 你可以到 [开发者社区](https://dev.agora.io/cn/) 提问 -- 如果有售前咨询问题, 可以拨打 400 632 6626,或加入官方Q群 12742516 提问 -- 如果需要售后技术支持, 你可以在 [Agora Dashboard](https://dashboard.agora.io) 提交工单 -- 如果发现了示例代码的 bug, 欢迎提交 [issue](https://github.com/AgoraIO/Basic-Video-Call/issues) +- 若遇到问题需要开发者帮助,你可以到 [开发者社区](https://rtcdeveloper.com/) 提问 +- 如果发现了示例代码的 bug,欢迎提交 [issue](https://github.com/AgoraIO/Basic-Video-Call/issues) ## 代码许可 diff --git a/Group-Video/OpenVideoCall-Android/README.zh.yaml b/Group-Video/OpenVideoCall-Android/README.zh.yaml deleted file mode 100644 index ab06f2cc..00000000 --- a/Group-Video/OpenVideoCall-Android/README.zh.yaml +++ /dev/null @@ -1,54 +0,0 @@ -Meta: - name: Open Video Call for Android - # en or cn - lang: cn - version: 2.4.1 - # | 代表这里是字符串 - description: | - 这个开源示例项目演示了如何快速集成 Agora 视频 SDK,实现多人视频通话。 - - 在这个示例项目中包含了以下功能: - - - 加入通话和离开通话; - - 静音和解除静音; - - 关闭摄像头和打开摄像头; - - 切换前置摄像头和后置摄像头; - - 发送频道内消息; - - 选择分辨率、码率和帧率; - - 设置加密模式; - - 开启和关闭黑白滤镜; - - 你也可以在这里查看入门版的示例项目:[Agora-Android-Tutorial-1to1](https://github.com/AgoraIO/Basic-Video-Call/tree/master/One-to-One-Video/Agora-Android-Tutorial-1to1) - -Prerequisites: - - Android Studio 3.3 + - - 真实 Android 设备 (Nexus 5X 或者其它设备) - - 部分模拟器会存在功能缺失或者性能问题,所以推荐使用真机 - -QuickStart: - description: - 这个段落主要讲解了如何编译和运行实例程序。 - sections: - - title: 创建Agora账号并获取AppId - content: | - $_{APPID} - 5. 将 AppID 填写进 "app/src/main/res/values/strings_config.xml" - ``` - <#YOUR APP ID#> - - - <#YOUR TOKEN#> - ``` - - title: 集成 Agora 视频 SDK - content: | - $_{ANDROID_INTEGRATE} - - title: 启动应用程序 - content: | - $_{ANDROID_RUN} - -Resources: - document: https://docs.agora.io/cn/ - issue: https://github.com/AgoraIO/Basic-Video-Call/issues - -License: - type: MIT \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Android/app/build.gradle b/Group-Video/OpenVideoCall-Android/app/build.gradle index c7e2d773..909fe9e2 100644 --- a/Group-Video/OpenVideoCall-Android/app/build.gradle +++ b/Group-Video/OpenVideoCall-Android/app/build.gradle @@ -45,12 +45,14 @@ dependencies { implementation 'com.android.support:appcompat-v7:28.0.0' implementation 'com.android.support:support-v4:28.0.0' implementation 'com.android.support:design:28.0.0' - implementation 'org.slf4j:slf4j-api:1.7.21' + implementation 'org.slf4j:slf4j-api:1.7.25' implementation 'com.github.tony19:logback-android-core:1.1.1-4' implementation('com.github.tony19:logback-android-classic:1.1.1-4') { // workaround issue #73 exclude group: 'com.google.android', module: 'android' } + + implementation 'io.agora.rtc:full-sdk:2.9.2' androidTestImplementation 'com.android.support.test:rules:1.0.2' androidTestImplementation 'com.jayway.android.robotium:robotium-solo:5.6.3' } diff --git a/Group-Video/OpenVideoCall-Android/app/src/main/java/io/agora/openvcall/AGApplication.java b/Group-Video/OpenVideoCall-Android/app/src/main/java/io/agora/openvcall/AGApplication.java index db047955..15bbf998 100644 --- a/Group-Video/OpenVideoCall-Android/app/src/main/java/io/agora/openvcall/AGApplication.java +++ b/Group-Video/OpenVideoCall-Android/app/src/main/java/io/agora/openvcall/AGApplication.java @@ -1,35 +1,78 @@ package io.agora.openvcall; import android.app.Application; +import android.content.Context; +import android.text.TextUtils; +import android.util.Log; + +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import io.agora.openvcall.model.AGEventHandler; import io.agora.openvcall.model.CurrentUserSettings; -import io.agora.openvcall.model.WorkerThread; +import io.agora.openvcall.model.EngineConfig; +import io.agora.openvcall.model.MyEngineEventHandler; +import io.agora.rtc.Constants; +import io.agora.rtc.RtcEngine; public class AGApplication extends Application { + private CurrentUserSettings mVideoSettings = new CurrentUserSettings(); - private WorkerThread mWorkerThread; + private final Logger log = LoggerFactory.getLogger(this.getClass()); + private RtcEngine mRtcEngine; + private EngineConfig mConfig; + private MyEngineEventHandler mEventHandler; - public synchronized void initWorkerThread() { - if (mWorkerThread == null) { - mWorkerThread = new WorkerThread(getApplicationContext()); - mWorkerThread.start(); + public RtcEngine rtcEngine() { + return mRtcEngine; + } - mWorkerThread.waitForReady(); - } + public EngineConfig config() { + return mConfig; + } + + public CurrentUserSettings userSettings() { + return mVideoSettings; + } + + public void addEventHandler(AGEventHandler handler) { + mEventHandler.addEventHandler(handler); } - public synchronized WorkerThread getWorkerThread() { - return mWorkerThread; + public void remoteEventHandler(AGEventHandler handler) { + mEventHandler.removeEventHandler(handler); } - public synchronized void deInitWorkerThread() { - mWorkerThread.exit(); + @Override + public void onCreate() { + super.onCreate(); + createRtcEngine(); + } + + private void createRtcEngine() { + Context context = getApplicationContext(); + String appId = context.getString(R.string.agora_app_id); + if (TextUtils.isEmpty(appId)) { + throw new RuntimeException("NEED TO use your App ID, get your own ID at https://dashboard.agora.io/"); + } + + mEventHandler = new MyEngineEventHandler(); try { - mWorkerThread.join(); - } catch (InterruptedException e) { - e.printStackTrace(); + mRtcEngine = RtcEngine.create(context, appId, mEventHandler); + } catch (Exception e) { + log.error(Log.getStackTraceString(e)); + throw new RuntimeException("NEED TO check rtc sdk init fatal error\n" + Log.getStackTraceString(e)); } - mWorkerThread = null; + + mRtcEngine.setChannelProfile(Constants.CHANNEL_PROFILE_COMMUNICATION); + mRtcEngine.enableVideo(); + mRtcEngine.enableAudioVolumeIndication(200, 3, false); + + mConfig = new EngineConfig(); } - public static final CurrentUserSettings mVideoSettings = new CurrentUserSettings(); + @Override + public void onTerminate() { + super.onTerminate(); + } } diff --git a/Group-Video/OpenVideoCall-Android/app/src/main/java/io/agora/openvcall/model/EngineConfig.java b/Group-Video/OpenVideoCall-Android/app/src/main/java/io/agora/openvcall/model/EngineConfig.java index ecfe05f7..13489df5 100644 --- a/Group-Video/OpenVideoCall-Android/app/src/main/java/io/agora/openvcall/model/EngineConfig.java +++ b/Group-Video/OpenVideoCall-Android/app/src/main/java/io/agora/openvcall/model/EngineConfig.java @@ -9,6 +9,6 @@ public void reset() { mChannel = null; } - EngineConfig() { + public EngineConfig() { } } diff --git a/Group-Video/OpenVideoCall-Android/app/src/main/java/io/agora/openvcall/model/MyEngineEventHandler.java b/Group-Video/OpenVideoCall-Android/app/src/main/java/io/agora/openvcall/model/MyEngineEventHandler.java index 4230f6c3..5cf30190 100644 --- a/Group-Video/OpenVideoCall-Android/app/src/main/java/io/agora/openvcall/model/MyEngineEventHandler.java +++ b/Group-Video/OpenVideoCall-Android/app/src/main/java/io/agora/openvcall/model/MyEngineEventHandler.java @@ -1,8 +1,5 @@ package io.agora.openvcall.model; -import android.content.Context; - -import io.agora.rtc.Constants; import io.agora.rtc.IRtcEngineEventHandler; import io.agora.rtc.RtcEngine; @@ -13,17 +10,8 @@ import java.util.Iterator; import java.util.concurrent.ConcurrentHashMap; -public class MyEngineEventHandler { - - public MyEngineEventHandler(Context ctx, EngineConfig config) { - this.mContext = ctx; - this.mConfig = config; - } - - private final EngineConfig mConfig; - - private final Context mContext; - +public class MyEngineEventHandler extends IRtcEngineEventHandler { + private final Logger log = LoggerFactory.getLogger(this.getClass()); private final ConcurrentHashMap mEventHandlerList = new ConcurrentHashMap<>(); public void addEventHandler(AGEventHandler handler) { @@ -34,236 +22,219 @@ public void removeEventHandler(AGEventHandler handler) { this.mEventHandlerList.remove(handler); } - final IRtcEngineEventHandler mRtcEventHandler = new IRtcEngineEventHandler() { - private final Logger log = LoggerFactory.getLogger(this.getClass()); - - @Override - public void onFirstRemoteVideoDecoded(int uid, int width, int height, int elapsed) { - log.debug("onFirstRemoteVideoDecoded " + (uid & 0xFFFFFFFFL) + " " + width + " " + height + " " + elapsed); + @Override + public void onFirstRemoteVideoDecoded(int uid, int width, int height, int elapsed) { + log.debug("onFirstRemoteVideoDecoded " + (uid & 0xFFFFFFFFL) + " " + width + " " + height + " " + elapsed); - Iterator it = mEventHandlerList.keySet().iterator(); - while (it.hasNext()) { - AGEventHandler handler = it.next(); - if (handler instanceof DuringCallEventHandler) { - ((DuringCallEventHandler) handler).onFirstRemoteVideoDecoded(uid, width, height, elapsed); - } + Iterator it = mEventHandlerList.keySet().iterator(); + while (it.hasNext()) { + AGEventHandler handler = it.next(); + if (handler instanceof DuringCallEventHandler) { + ((DuringCallEventHandler) handler).onFirstRemoteVideoDecoded(uid, width, height, elapsed); } } + } - @Override - public void onFirstLocalVideoFrame(int width, int height, int elapsed) { - log.debug("onFirstLocalVideoFrame " + width + " " + height + " " + elapsed); - } + @Override + public void onFirstLocalVideoFrame(int width, int height, int elapsed) { + log.debug("onFirstLocalVideoFrame " + width + " " + height + " " + elapsed); + } - @Override - public void onUserJoined(int uid, int elapsed) { - log.debug("onUserJoined " + (uid & 0xFFFFFFFFL) + elapsed); + @Override + public void onUserJoined(int uid, int elapsed) { + log.debug("onUserJoined " + (uid & 0xFFFFFFFFL) + elapsed); - Iterator it = mEventHandlerList.keySet().iterator(); - while (it.hasNext()) { - AGEventHandler handler = it.next(); - if (handler instanceof DuringCallEventHandler) { - ((DuringCallEventHandler) handler).onUserJoined(uid); - } + Iterator it = mEventHandlerList.keySet().iterator(); + while (it.hasNext()) { + AGEventHandler handler = it.next(); + if (handler instanceof DuringCallEventHandler) { + ((DuringCallEventHandler) handler).onUserJoined(uid); } } + } + + @Override + public void onUserOffline(int uid, int reason) { + log.debug("onUserOffline " + (uid & 0xFFFFFFFFL) + " " + reason); - @Override - public void onUserOffline(int uid, int reason) { - log.debug("onUserOffline " + (uid & 0xFFFFFFFFL) + " " + reason); - - // FIXME this callback may return times - Iterator it = mEventHandlerList.keySet().iterator(); - while (it.hasNext()) { - AGEventHandler handler = it.next(); - if (handler instanceof DuringCallEventHandler) { - ((DuringCallEventHandler) handler).onUserOffline(uid, reason); - } + // FIXME this callback may return times + Iterator it = mEventHandlerList.keySet().iterator(); + while (it.hasNext()) { + AGEventHandler handler = it.next(); + if (handler instanceof DuringCallEventHandler) { + ((DuringCallEventHandler) handler).onUserOffline(uid, reason); } } + } - @Override - public void onUserMuteVideo(int uid, boolean muted) { - log.debug("onUserMuteVideo " + (uid & 0xFFFFFFFFL) + " " + muted); + @Override + public void onUserMuteVideo(int uid, boolean muted) { + log.debug("onUserMuteVideo " + (uid & 0xFFFFFFFFL) + " " + muted); - Iterator it = mEventHandlerList.keySet().iterator(); - while (it.hasNext()) { - AGEventHandler handler = it.next(); - if (handler instanceof DuringCallEventHandler) { - ((DuringCallEventHandler) handler).onExtraCallback(AGEventHandler.EVENT_TYPE_ON_USER_VIDEO_MUTED, uid, muted); - } + Iterator it = mEventHandlerList.keySet().iterator(); + while (it.hasNext()) { + AGEventHandler handler = it.next(); + if (handler instanceof DuringCallEventHandler) { + ((DuringCallEventHandler) handler).onExtraCallback(AGEventHandler.EVENT_TYPE_ON_USER_VIDEO_MUTED, uid, muted); } } + } - @Override - public void onRtcStats(RtcStats stats) { - } + @Override + public void onRtcStats(RtcStats stats) { + } - @Override - public void onRemoteVideoStats(RemoteVideoStats stats) { - log.debug("onRemoteVideoStats " + stats.uid + " " + stats.delay + " " + stats.receivedBitrate + " " + stats.rendererOutputFrameRate + " " + stats.width + " " + stats.height); + @Override + public void onRemoteVideoStats(RemoteVideoStats stats) { + log.debug("onRemoteVideoStats " + stats.uid + " " + stats.delay + " " + stats.receivedBitrate + " " + stats.rendererOutputFrameRate + " " + stats.width + " " + stats.height); - Iterator it = mEventHandlerList.keySet().iterator(); - while (it.hasNext()) { - AGEventHandler handler = it.next(); - if (handler instanceof DuringCallEventHandler) { - ((DuringCallEventHandler) handler).onExtraCallback(AGEventHandler.EVENT_TYPE_ON_USER_VIDEO_STATS, stats); - } + Iterator it = mEventHandlerList.keySet().iterator(); + while (it.hasNext()) { + AGEventHandler handler = it.next(); + if (handler instanceof DuringCallEventHandler) { + ((DuringCallEventHandler) handler).onExtraCallback(AGEventHandler.EVENT_TYPE_ON_USER_VIDEO_STATS, stats); } } + } - @Override - public void onAudioVolumeIndication(AudioVolumeInfo[] speakerInfos, int totalVolume) { - if (speakerInfos == null) { - // quick and dirty fix for crash - // TODO should reset UI for no sound - return; - } + @Override + public void onAudioVolumeIndication(AudioVolumeInfo[] speakerInfos, int totalVolume) { + if (speakerInfos == null) { + // quick and dirty fix for crash + // TODO should reset UI for no sound + return; + } - Iterator it = mEventHandlerList.keySet().iterator(); - while (it.hasNext()) { - AGEventHandler handler = it.next(); - if (handler instanceof DuringCallEventHandler) { - ((DuringCallEventHandler) handler).onExtraCallback(AGEventHandler.EVENT_TYPE_ON_SPEAKER_STATS, (Object) speakerInfos); - } + Iterator it = mEventHandlerList.keySet().iterator(); + while (it.hasNext()) { + AGEventHandler handler = it.next(); + if (handler instanceof DuringCallEventHandler) { + ((DuringCallEventHandler) handler).onExtraCallback(AGEventHandler.EVENT_TYPE_ON_SPEAKER_STATS, (Object) speakerInfos); } } + } - @Override - public void onLeaveChannel(RtcStats stats) { + @Override + public void onLeaveChannel(RtcStats stats) { - } + } - @Override - public void onLastmileQuality(int quality) { - log.debug("onLastmileQuality " + quality); - Iterator it = mEventHandlerList.keySet().iterator(); - while (it.hasNext()) { - AGEventHandler handler = it.next(); - if (handler instanceof BeforeCallEventHandler) { - ((BeforeCallEventHandler) handler).onLastmileQuality(quality); - } + @Override + public void onLastmileQuality(int quality) { + log.debug("onLastmileQuality " + quality); + Iterator it = mEventHandlerList.keySet().iterator(); + while (it.hasNext()) { + AGEventHandler handler = it.next(); + if (handler instanceof BeforeCallEventHandler) { + ((BeforeCallEventHandler) handler).onLastmileQuality(quality); } } + } - @Override - public void onLastmileProbeResult(IRtcEngineEventHandler.LastmileProbeResult result) { - log.debug("onLastmileProbeResult " + result); - Iterator it = mEventHandlerList.keySet().iterator(); - while (it.hasNext()) { - AGEventHandler handler = it.next(); - if (handler instanceof BeforeCallEventHandler) { - ((BeforeCallEventHandler) handler).onLastmileProbeResult(result); - } + @Override + public void onLastmileProbeResult(LastmileProbeResult result) { + log.debug("onLastmileProbeResult " + result); + Iterator it = mEventHandlerList.keySet().iterator(); + while (it.hasNext()) { + AGEventHandler handler = it.next(); + if (handler instanceof BeforeCallEventHandler) { + ((BeforeCallEventHandler) handler).onLastmileProbeResult(result); } } + } - @Override - public void onError(int error) { - log.debug("onError " + error + " " + RtcEngine.getErrorDescription(error)); + @Override + public void onError(int error) { + log.debug("onError " + error + " " + RtcEngine.getErrorDescription(error)); - Iterator it = mEventHandlerList.keySet().iterator(); - while (it.hasNext()) { - AGEventHandler handler = it.next(); - if (handler instanceof DuringCallEventHandler) { - ((DuringCallEventHandler) handler).onExtraCallback(AGEventHandler.EVENT_TYPE_ON_AGORA_MEDIA_ERROR, error, RtcEngine.getErrorDescription(error)); - } + Iterator it = mEventHandlerList.keySet().iterator(); + while (it.hasNext()) { + AGEventHandler handler = it.next(); + if (handler instanceof DuringCallEventHandler) { + ((DuringCallEventHandler) handler).onExtraCallback(AGEventHandler.EVENT_TYPE_ON_AGORA_MEDIA_ERROR, error, RtcEngine.getErrorDescription(error)); } } + } - @Override - public void onStreamMessage(int uid, int streamId, byte[] data) { - log.debug("onStreamMessage " + (uid & 0xFFFFFFFFL) + " " + streamId + " " + Arrays.toString(data)); + @Override + public void onStreamMessage(int uid, int streamId, byte[] data) { + log.debug("onStreamMessage " + (uid & 0xFFFFFFFFL) + " " + streamId + " " + Arrays.toString(data)); - Iterator it = mEventHandlerList.keySet().iterator(); - while (it.hasNext()) { - AGEventHandler handler = it.next(); - if (handler instanceof DuringCallEventHandler) { - ((DuringCallEventHandler) handler).onExtraCallback(AGEventHandler.EVENT_TYPE_ON_DATA_CHANNEL_MSG, uid, data); - } + Iterator it = mEventHandlerList.keySet().iterator(); + while (it.hasNext()) { + AGEventHandler handler = it.next(); + if (handler instanceof DuringCallEventHandler) { + ((DuringCallEventHandler) handler).onExtraCallback(AGEventHandler.EVENT_TYPE_ON_DATA_CHANNEL_MSG, uid, data); } } + } - public void onStreamMessageError(int uid, int streamId, int error, int missed, int cached) { - log.warn("onStreamMessageError " + (uid & 0xFFFFFFFFL) + " " + streamId + " " + error + " " + missed + " " + cached); + public void onStreamMessageError(int uid, int streamId, int error, int missed, int cached) { + log.warn("onStreamMessageError " + (uid & 0xFFFFFFFFL) + " " + streamId + " " + error + " " + missed + " " + cached); - Iterator it = mEventHandlerList.keySet().iterator(); - while (it.hasNext()) { - AGEventHandler handler = it.next(); - if (handler instanceof DuringCallEventHandler) { - ((DuringCallEventHandler) handler).onExtraCallback(AGEventHandler.EVENT_TYPE_ON_AGORA_MEDIA_ERROR, error, "on stream msg error " + (uid & 0xFFFFFFFFL) + " " + missed + " " + cached); - } + Iterator it = mEventHandlerList.keySet().iterator(); + while (it.hasNext()) { + AGEventHandler handler = it.next(); + if (handler instanceof DuringCallEventHandler) { + ((DuringCallEventHandler) handler).onExtraCallback(AGEventHandler.EVENT_TYPE_ON_AGORA_MEDIA_ERROR, error, "on stream msg error " + (uid & 0xFFFFFFFFL) + " " + missed + " " + cached); } } + } - @Override - public void onConnectionLost() { - log.debug("onConnectionLost"); + @Override + public void onConnectionLost() { + log.debug("onConnectionLost"); - Iterator it = mEventHandlerList.keySet().iterator(); - while (it.hasNext()) { - AGEventHandler handler = it.next(); - if (handler instanceof DuringCallEventHandler) { - ((DuringCallEventHandler) handler).onExtraCallback(AGEventHandler.EVENT_TYPE_ON_APP_ERROR, ConstantApp.AppError.NO_CONNECTION_ERROR); - } + Iterator it = mEventHandlerList.keySet().iterator(); + while (it.hasNext()) { + AGEventHandler handler = it.next(); + if (handler instanceof DuringCallEventHandler) { + ((DuringCallEventHandler) handler).onExtraCallback(AGEventHandler.EVENT_TYPE_ON_APP_ERROR, ConstantApp.AppError.NO_CONNECTION_ERROR); } } + } - @Override - public void onJoinChannelSuccess(String channel, int uid, int elapsed) { - log.debug("onJoinChannelSuccess " + channel + " " + (uid & 0xFFFFFFFFL) + "(" + uid + ") " + elapsed); - - mConfig.mUid = uid; + @Override + public void onJoinChannelSuccess(String channel, int uid, int elapsed) { + log.debug("onJoinChannelSuccess " + channel + " " + (uid & 0xFFFFFFFFL) + "(" + uid + ") " + elapsed); - Iterator it = mEventHandlerList.keySet().iterator(); - while (it.hasNext()) { - AGEventHandler handler = it.next(); - if (handler instanceof DuringCallEventHandler) { - ((DuringCallEventHandler) handler).onJoinChannelSuccess(channel, uid, elapsed); - } + Iterator it = mEventHandlerList.keySet().iterator(); + while (it.hasNext()) { + AGEventHandler handler = it.next(); + if (handler instanceof DuringCallEventHandler) { + ((DuringCallEventHandler) handler).onJoinChannelSuccess(channel, uid, elapsed); } } + } - public void onRejoinChannelSuccess(String channel, int uid, int elapsed) { - log.debug("onRejoinChannelSuccess " + channel + " " + uid + " " + elapsed); - } - - @Override - public void onAudioRouteChanged(int routing) { - log.debug("onAudioRouteChanged " + routing); + @Override + public void onAudioRouteChanged(int routing) { + log.debug("onAudioRouteChanged " + routing); - Iterator it = mEventHandlerList.keySet().iterator(); - while (it.hasNext()) { - AGEventHandler handler = it.next(); - if (handler instanceof DuringCallEventHandler) { - ((DuringCallEventHandler) handler).onExtraCallback(AGEventHandler.EVENT_TYPE_ON_AUDIO_ROUTE_CHANGED, routing); - } + Iterator it = mEventHandlerList.keySet().iterator(); + while (it.hasNext()) { + AGEventHandler handler = it.next(); + if (handler instanceof DuringCallEventHandler) { + ((DuringCallEventHandler) handler).onExtraCallback(AGEventHandler.EVENT_TYPE_ON_AUDIO_ROUTE_CHANGED, routing); } } + } - public void onWarning(int warn) { - log.debug("onWarning " + warn); - - String msg = "Check io.agora.rtc.Constants for details"; + public void onWarning(int warn) { + log.debug("onWarning " + warn); - Iterator it = mEventHandlerList.keySet().iterator(); - while (it.hasNext()) { - AGEventHandler handler = it.next(); - if (handler instanceof DuringCallEventHandler) { - ((DuringCallEventHandler) handler).onExtraCallback(AGEventHandler.EVENT_TYPE_ON_AGORA_MEDIA_ERROR, warn, msg); - } + String msg = "Check io.agora.rtc.Constants for details"; + Iterator it = mEventHandlerList.keySet().iterator(); + while (it.hasNext()) { + AGEventHandler handler = it.next(); + if (handler instanceof DuringCallEventHandler) { + ((DuringCallEventHandler) handler).onExtraCallback(AGEventHandler.EVENT_TYPE_ON_AGORA_MEDIA_ERROR, warn, msg); } } + } - @Override - public void onAudioMixingStateChanged(int state, int errorCode) { - log.debug("onAudioMixingStateChanged() state = [" + state + "], errorCode = [" + errorCode + "]"); - } - - @Override - public void onAudioMixingFinished() { - log.debug("onAudioMixingFinished"); - } - }; - + @Override + public void onAudioMixingStateChanged(int state, int errorCode) { + log.debug("onAudioMixingStateChanged() state = [" + state + "], errorCode = [" + errorCode + "]"); + } } diff --git a/Group-Video/OpenVideoCall-Android/app/src/main/java/io/agora/openvcall/model/WorkerThread.java b/Group-Video/OpenVideoCall-Android/app/src/main/java/io/agora/openvcall/model/WorkerThread.java deleted file mode 100644 index 32bdea6c..00000000 --- a/Group-Video/OpenVideoCall-Android/app/src/main/java/io/agora/openvcall/model/WorkerThread.java +++ /dev/null @@ -1,299 +0,0 @@ -package io.agora.openvcall.model; - -import android.content.Context; -import android.content.SharedPreferences; -import android.os.Handler; -import android.os.Looper; -import android.os.Message; -import android.preference.PreferenceManager; -import android.provider.Settings; -import android.text.TextUtils; -import android.util.Log; -import android.view.SurfaceView; - -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; - -import io.agora.openvcall.R; -import io.agora.propeller.Constant; -import io.agora.rtc.Constants; -import io.agora.rtc.RtcEngine; -import io.agora.rtc.video.VideoCanvas; -import io.agora.rtc.video.VideoEncoderConfiguration; - -public class WorkerThread extends Thread { - private final static Logger log = LoggerFactory.getLogger(WorkerThread.class); - - private final Context mContext; - - private static final int ACTION_WORKER_THREAD_QUIT = 0X1010; // quit this thread - - private static final int ACTION_WORKER_JOIN_CHANNEL = 0X2010; - - private static final int ACTION_WORKER_LEAVE_CHANNEL = 0X2011; - - private static final int ACTION_WORKER_CONFIG_ENGINE = 0X2012; - - private static final int ACTION_WORKER_PREVIEW = 0X2014; - - private static final class WorkerThreadHandler extends Handler { - - private WorkerThread mWorkerThread; - - WorkerThreadHandler(WorkerThread thread) { - this.mWorkerThread = thread; - } - - public void release() { - mWorkerThread = null; - } - - @Override - public void handleMessage(Message msg) { - if (this.mWorkerThread == null) { - log.warn("handler is already released! " + msg.what); - return; - } - - switch (msg.what) { - case ACTION_WORKER_THREAD_QUIT: - mWorkerThread.exit(); - break; - case ACTION_WORKER_JOIN_CHANNEL: - String[] data = (String[]) msg.obj; - mWorkerThread.joinChannel(data[0], msg.arg1); - break; - case ACTION_WORKER_LEAVE_CHANNEL: - String channel = (String) msg.obj; - mWorkerThread.leaveChannel(channel); - break; - case ACTION_WORKER_CONFIG_ENGINE: - Object[] configData = (Object[]) msg.obj; - mWorkerThread.configEngine((VideoEncoderConfiguration.VideoDimensions) configData[0], (VideoEncoderConfiguration.FRAME_RATE) configData[1], (String) configData[2], (String) configData[3]); - break; - case ACTION_WORKER_PREVIEW: - Object[] previewData = (Object[]) msg.obj; - mWorkerThread.preview((boolean) previewData[0], (SurfaceView) previewData[1], (int) previewData[2]); - break; - } - } - } - - private WorkerThreadHandler mWorkerHandler; - - private boolean mReady; - - public final void waitForReady() { - while (!mReady) { - try { - Thread.sleep(20); - } catch (InterruptedException e) { - e.printStackTrace(); - } - log.debug("wait for " + WorkerThread.class.getSimpleName()); - } - } - - @Override - public void run() { - log.trace("start to run"); - Looper.prepare(); - - mWorkerHandler = new WorkerThreadHandler(this); - - ensureRtcEngineReadyLock(); - - mReady = true; - - // enter thread looper - Looper.loop(); - } - - private RtcEngine mRtcEngine; - - public final void enablePreProcessor() { - if (Constant.BEAUTY_EFFECT_ENABLED) { - mRtcEngine.setBeautyEffectOptions(true, Constant.BEAUTY_OPTIONS); - } - } - - public final void setBeautyEffectParameters(float lightness, float smoothness, float redness) { - Constant.BEAUTY_OPTIONS.lighteningLevel = lightness; - Constant.BEAUTY_OPTIONS.smoothnessLevel = smoothness; - Constant.BEAUTY_OPTIONS.rednessLevel = redness; - } - - public final void disablePreProcessor() { - // do not support null when setBeautyEffectOptions to false - mRtcEngine.setBeautyEffectOptions(false, Constant.BEAUTY_OPTIONS); - } - - public final void joinChannel(final String channel, int uid) { - if (Thread.currentThread() != this) { - log.warn("joinChannel() - worker thread asynchronously " + channel + " " + uid); - Message envelop = new Message(); - envelop.what = ACTION_WORKER_JOIN_CHANNEL; - envelop.obj = new String[]{channel}; - envelop.arg1 = uid; - mWorkerHandler.sendMessage(envelop); - return; - } - - ensureRtcEngineReadyLock(); - - String accessToken = mContext.getString(R.string.agora_access_token); - if (TextUtils.equals(accessToken, "") || TextUtils.equals(accessToken, "#YOUR ACCESS TOKEN#")) { - accessToken = null; // default, no token - } - - mRtcEngine.joinChannel(accessToken, channel, "OpenVCall", uid); - - mEngineConfig.mChannel = channel; - - enablePreProcessor(); - log.debug("joinChannel " + channel + " " + uid); - } - - public final void leaveChannel(String channel) { - if (Thread.currentThread() != this) { - log.warn("leaveChannel() - worker thread asynchronously " + channel); - Message envelop = new Message(); - envelop.what = ACTION_WORKER_LEAVE_CHANNEL; - envelop.obj = channel; - mWorkerHandler.sendMessage(envelop); - return; - } - - if (mRtcEngine != null) { - mRtcEngine.leaveChannel(); - mRtcEngine.enableVideo(); - } - - disablePreProcessor(); - - mEngineConfig.reset(); - log.debug("leaveChannel " + channel); - } - - private EngineConfig mEngineConfig; - - public final EngineConfig getEngineConfig() { - return mEngineConfig; - } - - private final MyEngineEventHandler mEngineEventHandler; - - public final void configEngine(VideoEncoderConfiguration.VideoDimensions videoDimension, VideoEncoderConfiguration.FRAME_RATE fps, String encryptionKey, String encryptionMode) { - if (Thread.currentThread() != this) { - log.warn("configEngine() - worker thread asynchronously " + videoDimension + " " + fps + " " + encryptionMode); - Message envelop = new Message(); - envelop.what = ACTION_WORKER_CONFIG_ENGINE; - envelop.obj = new Object[]{videoDimension, fps, encryptionKey, encryptionMode}; - mWorkerHandler.sendMessage(envelop); - return; - } - - ensureRtcEngineReadyLock(); - - if (!TextUtils.isEmpty(encryptionKey)) { - mRtcEngine.setEncryptionMode(encryptionMode); - - mRtcEngine.setEncryptionSecret(encryptionKey); - } - - // mRtcEngine.setVideoProfile(mEngineConfig.mVideoProfile, false); // for sdk earlier than 2.3.0 - mRtcEngine.setVideoEncoderConfiguration(new VideoEncoderConfiguration(videoDimension, - fps, - VideoEncoderConfiguration.STANDARD_BITRATE, - VideoEncoderConfiguration.ORIENTATION_MODE.ORIENTATION_MODE_FIXED_PORTRAIT)); - - log.debug("configEngine " + videoDimension + " " + fps + " " + encryptionMode); - } - - public final void preview(boolean start, SurfaceView view, int uid) { - if (Thread.currentThread() != this) { - log.warn("preview() - worker thread asynchronously " + start + " " + view + " " + (uid & 0XFFFFFFFFL)); - Message envelop = new Message(); - envelop.what = ACTION_WORKER_PREVIEW; - envelop.obj = new Object[]{start, view, uid}; - mWorkerHandler.sendMessage(envelop); - return; - } - - ensureRtcEngineReadyLock(); - if (start) { - mRtcEngine.setupLocalVideo(new VideoCanvas(view, VideoCanvas.RENDER_MODE_HIDDEN, uid)); - mRtcEngine.startPreview(); - } else { - mRtcEngine.stopPreview(); - } - } - - public static String getDeviceID(Context context) { - // XXX according to the API docs, this value may change after factory reset - // use Android id as device id - return Settings.Secure.getString(context.getContentResolver(), Settings.Secure.ANDROID_ID); - } - - private RtcEngine ensureRtcEngineReadyLock() { - if (mRtcEngine == null) { - String appId = mContext.getString(R.string.agora_app_id); - if (TextUtils.isEmpty(appId)) { - throw new RuntimeException("NEED TO use your App ID, get your own ID at https://dashboard.agora.io/"); - } - try { - mRtcEngine = RtcEngine.create(mContext, appId, mEngineEventHandler.mRtcEventHandler); - } catch (Exception e) { - log.error(Log.getStackTraceString(e)); - throw new RuntimeException("NEED TO check rtc sdk init fatal error\n" + Log.getStackTraceString(e)); - } - mRtcEngine.setChannelProfile(Constants.CHANNEL_PROFILE_COMMUNICATION); - mRtcEngine.enableVideo(); - mRtcEngine.enableAudioVolumeIndication(200, 3); // 200 ms - } - return mRtcEngine; - } - - public MyEngineEventHandler eventHandler() { - return mEngineEventHandler; - } - - public RtcEngine getRtcEngine() { - return mRtcEngine; - } - - /** - * call this method to exit - * should ONLY call this method when this thread is running - */ - public final void exit() { - if (Thread.currentThread() != this) { - log.warn("exit() - exit app thread asynchronously"); - mWorkerHandler.sendEmptyMessage(ACTION_WORKER_THREAD_QUIT); - return; - } - - mReady = false; - - // TODO should remove all pending(read) messages - - log.debug("exit() > start"); - - // exit thread looper - Looper.myLooper().quit(); - - mWorkerHandler.release(); - - log.debug("exit() > end"); - } - - public WorkerThread(Context context) { - this.mContext = context; - - this.mEngineConfig = new EngineConfig(); - SharedPreferences pref = PreferenceManager.getDefaultSharedPreferences(context); - this.mEngineConfig.mUid = pref.getInt(ConstantApp.PrefManager.PREF_PROPERTY_UID, 0); - - this.mEngineEventHandler = new MyEngineEventHandler(mContext, this.mEngineConfig); - } -} diff --git a/Group-Video/OpenVideoCall-Android/app/src/main/java/io/agora/openvcall/ui/BaseActivity.java b/Group-Video/OpenVideoCall-Android/app/src/main/java/io/agora/openvcall/ui/BaseActivity.java index 8aefabf5..6f727989 100644 --- a/Group-Video/OpenVideoCall-Android/app/src/main/java/io/agora/openvcall/ui/BaseActivity.java +++ b/Group-Video/OpenVideoCall-Android/app/src/main/java/io/agora/openvcall/ui/BaseActivity.java @@ -6,21 +6,23 @@ import android.os.Build; import android.os.Bundle; import android.os.Handler; -import android.os.Looper; import android.support.annotation.NonNull; import android.support.v4.app.ActivityCompat; import android.support.v4.content.ContextCompat; import android.support.v7.app.AppCompatActivity; +import android.text.TextUtils; import android.util.DisplayMetrics; import android.view.*; import android.view.inputmethod.InputMethodManager; -import android.widget.EditText; import android.widget.Toast; import io.agora.openvcall.AGApplication; -import io.agora.openvcall.BuildConfig; +import io.agora.openvcall.R; import io.agora.openvcall.model.*; import io.agora.propeller.Constant; import io.agora.rtc.RtcEngine; +import io.agora.rtc.video.VideoCanvas; +import io.agora.rtc.video.VideoEncoderConfiguration; + import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -52,7 +54,7 @@ public void onGlobalLayout() { protected abstract void deInitUIandEvent(); - protected void workerThreadReady() { + protected void permissionGranted() { } @Override @@ -93,26 +95,6 @@ public final void closeIME(View v) { v.clearFocus(); } - public final void closeIMEWithoutFocus(View v) { - InputMethodManager mgr = (InputMethodManager) getSystemService(INPUT_METHOD_SERVICE); - mgr.hideSoftInputFromWindow(v.getWindowToken(), 0); // 0 force close IME - } - - public void openIME(final EditText v) { - final boolean focus = v.requestFocus(); - if (v.hasFocus()) { - final Handler handler = new Handler(Looper.getMainLooper()); - handler.post(new Runnable() { - @Override - public void run() { - InputMethodManager mgr = (InputMethodManager) getSystemService(INPUT_METHOD_SERVICE); - boolean result = mgr.showSoftInput(v, InputMethodManager.SHOW_FORCED); - log.debug("openIME " + focus + " " + result); - } - }); - } - } - public boolean checkSelfPermission(String permission, int requestCode) { log.debug("checkSelfPermission " + permission + " " + requestCode); if (ContextCompat.checkSelfPermission(this, @@ -126,26 +108,33 @@ public boolean checkSelfPermission(String permission, int requestCode) { } if (Manifest.permission.CAMERA.equals(permission)) { - ((AGApplication) getApplication()).initWorkerThread(); - workerThreadReady(); + permissionGranted(); } return true; } + protected AGApplication application() { + return (AGApplication) getApplication(); + } + protected RtcEngine rtcEngine() { - return ((AGApplication) getApplication()).getWorkerThread().getRtcEngine(); + return application().rtcEngine(); } - protected final WorkerThread worker() { - return ((AGApplication) getApplication()).getWorkerThread(); + protected EngineConfig config() { + return application().config(); } - protected final EngineConfig config() { - return ((AGApplication) getApplication()).getWorkerThread().getEngineConfig(); + protected void addEventHandler(AGEventHandler handler) { + application().addEventHandler(handler); } - protected final MyEngineEventHandler event() { - return ((AGApplication) getApplication()).getWorkerThread().eventHandler(); + protected void removeEventHandler(AGEventHandler handler) { + application().remoteEventHandler(handler); + } + + protected CurrentUserSettings vSettings() { + return application().userSettings(); } public final void showLongToast(final String msg) { @@ -175,8 +164,7 @@ public void onRequestPermissionsResult(int requestCode, if (grantResults.length > 0 && grantResults[0] == PackageManager.PERMISSION_GRANTED) { checkSelfPermission(Manifest.permission.WRITE_EXTERNAL_STORAGE, ConstantApp.PERMISSION_REQ_ID_WRITE_EXTERNAL_STORAGE); - ((AGApplication) getApplication()).initWorkerThread(); - workerThreadReady(); + permissionGranted(); } else { finish(); } @@ -193,10 +181,6 @@ public void onRequestPermissionsResult(int requestCode, } } - protected CurrentUserSettings vSettings() { - return AGApplication.mVideoSettings; - } - protected int virtualKeyHeight() { boolean hasPermanentMenuKey = ViewConfiguration.get(getApplication()).hasPermanentMenuKey(); if (hasPermanentMenuKey) { @@ -275,10 +259,62 @@ protected final int getActionBarHeight() { return actionBarHeight; } - protected void initVersionInfo() { - String version = "V " + BuildConfig.VERSION_NAME + "(Build: " + BuildConfig.VERSION_CODE - + ", " + ConstantApp.APP_BUILD_DATE + ", SDK: " + Constant.MEDIA_SDK_VERSION + ")"; -// TextView textVersion = (TextView) findViewById(R.id.app_version); -// textVersion.setText(version); + protected void preview(boolean start, SurfaceView view, int uid) { + if (start) { + rtcEngine().setupLocalVideo(new VideoCanvas(view, VideoCanvas.RENDER_MODE_HIDDEN, uid)); + rtcEngine().startPreview(); + } else { + rtcEngine().stopPreview(); + } + } + + public final void joinChannel(final String channel, int uid) { + String accessToken = getApplicationContext().getString(R.string.agora_access_token); + if (TextUtils.equals(accessToken, "") || TextUtils.equals(accessToken, "<#YOUR ACCESS TOKEN#>")) { + accessToken = null; // default, no token + } + + rtcEngine().joinChannel(accessToken, channel, "OpenVCall", uid); + config().mChannel = channel; + enablePreProcessor(); + log.debug("joinChannel " + channel + " " + uid); + } + + public final void leaveChannel(String channel) { + log.debug("leaveChannel " + channel); + config().mChannel = null; + disablePreProcessor(); + rtcEngine().leaveChannel(); + config().reset(); + } + + protected void enablePreProcessor() { + if (Constant.BEAUTY_EFFECT_ENABLED) { + rtcEngine().setBeautyEffectOptions(true, Constant.BEAUTY_OPTIONS); + } + } + + public final void setBeautyEffectParameters(float lightness, float smoothness, float redness) { + Constant.BEAUTY_OPTIONS.lighteningLevel = lightness; + Constant.BEAUTY_OPTIONS.smoothnessLevel = smoothness; + Constant.BEAUTY_OPTIONS.rednessLevel = redness; + } + + protected void disablePreProcessor() { + // do not support null when setBeautyEffectOptions to false + rtcEngine().setBeautyEffectOptions(false, Constant.BEAUTY_OPTIONS); + } + + protected void configEngine(VideoEncoderConfiguration.VideoDimensions videoDimension, VideoEncoderConfiguration.FRAME_RATE fps, String encryptionKey, String encryptionMode) { + if (!TextUtils.isEmpty(encryptionKey)) { + rtcEngine().setEncryptionMode(encryptionMode); + rtcEngine().setEncryptionSecret(encryptionKey); + } + + log.debug("configEngine " + videoDimension + " " + fps + " " + encryptionMode); + rtcEngine().setVideoEncoderConfiguration(new VideoEncoderConfiguration(videoDimension, + fps, + VideoEncoderConfiguration.STANDARD_BITRATE, + VideoEncoderConfiguration.ORIENTATION_MODE.ORIENTATION_MODE_FIXED_PORTRAIT)); } } diff --git a/Group-Video/OpenVideoCall-Android/app/src/main/java/io/agora/openvcall/ui/CallActivity.java b/Group-Video/OpenVideoCall-Android/app/src/main/java/io/agora/openvcall/ui/CallActivity.java index 4fd4b904..82db84a7 100644 --- a/Group-Video/OpenVideoCall-Android/app/src/main/java/io/agora/openvcall/ui/CallActivity.java +++ b/Group-Video/OpenVideoCall-Android/app/src/main/java/io/agora/openvcall/ui/CallActivity.java @@ -117,13 +117,9 @@ public boolean onOptionsItemSelected(MenuItem item) { @Override protected void initUIandEvent() { - event().addEventHandler(this); + addEventHandler(this); + String channelName = getIntent().getStringExtra(ConstantApp.ACTION_KEY_CHANNEL_NAME); - Intent i = getIntent(); - - String channelName = i.getStringExtra(ConstantApp.ACTION_KEY_CHANNEL_NAME); - - // programmatically show channel name ActionBar ab = getSupportActionBar(); if (ab != null) { TextView channelNameView = ((TextView) findViewById(R.id.ovc_page_title)); @@ -142,7 +138,6 @@ protected void initUIandEvent() { mGridVideoViewContainer = (GridVideoViewContainer) findViewById(R.id.grid_video_view_container); mGridVideoViewContainer.setItemEventHandler(new RecyclerItemClickListener.OnItemClickListener() { - @Override public void onItemClick(View view, int position) { onBigVideoViewClicked(view, position); @@ -150,6 +145,7 @@ public void onItemClick(View view, int position) { @Override public void onItemLongClick(View view, int position) { + } @Override @@ -159,27 +155,24 @@ public void onItemDoubleClick(View view, int position) { }); SurfaceView surfaceV = RtcEngine.CreateRendererView(getApplicationContext()); - rtcEngine().setupLocalVideo(new VideoCanvas(surfaceV, VideoCanvas.RENDER_MODE_HIDDEN, 0)); + preview(true, surfaceV, 0); surfaceV.setZOrderOnTop(false); surfaceV.setZOrderMediaOverlay(false); mUidsList.put(0, surfaceV); // get first surface view mGridVideoViewContainer.initViewContainer(this, 0, mUidsList, mIsLandscape); // first is now full view - worker().preview(true, surfaceV, 0); initMessageList(); - notifyMessageChanged(new Message(new User(0, null), "start join " + channelName + " as " + (config().mUid & 0xFFFFFFFFL))); - worker().joinChannel(channelName, config().mUid); + joinChannel(channelName, config().mUid); optional(); } private void onBigVideoViewClicked(View view, int position) { log.debug("onItemClick " + view + " " + position + " " + mLayoutType); - toggleFullscreen(); } @@ -314,7 +307,6 @@ public void onClickHideIME(View view) { log.debug("onClickHideIME " + view); closeIME(findViewById(R.id.msg_content)); - findViewById(R.id.msg_input_container).setVisibility(View.GONE); findViewById(R.id.bottom_action_container).setVisibility(View.VISIBLE); } @@ -332,9 +324,7 @@ private void initMessageList() { private void notifyMessageChanged(Message msg) { mMsgList.add(msg); - int MAX_MESSAGE_COUNT = 16; - if (mMsgList.size() > MAX_MESSAGE_COUNT) { int toRemove = mMsgList.size() - MAX_MESSAGE_COUNT; for (int i = 0; i < toRemove; i++) { @@ -383,8 +373,7 @@ private int getVideoEncFpsIndex() { private void doConfigEngine(String encryptionKey, String encryptionMode) { VideoEncoderConfiguration.VideoDimensions videoDimension = ConstantApp.VIDEO_DIMENSIONS[getVideoEncResolutionIndex()]; VideoEncoderConfiguration.FRAME_RATE videoFps = ConstantApp.VIDEO_FPS[getVideoEncFpsIndex()]; - - worker().configEngine(videoDimension, videoFps, encryptionKey, encryptionMode); + configEngine(videoDimension, videoFps, encryptionKey, encryptionMode); } public void onSwitchCameraClicked(View view) { @@ -401,10 +390,10 @@ public void onFilterClicked(View view) { Constant.BEAUTY_EFFECT_ENABLED = !Constant.BEAUTY_EFFECT_ENABLED; if (Constant.BEAUTY_EFFECT_ENABLED) { - worker().setBeautyEffectParameters(Constant.BEAUTY_EFFECT_DEFAULT_LIGHTNESS, Constant.BEAUTY_EFFECT_DEFAULT_SMOOTHNESS, Constant.BEAUTY_EFFECT_DEFAULT_REDNESS); - worker().enablePreProcessor(); + setBeautyEffectParameters(Constant.BEAUTY_EFFECT_DEFAULT_LIGHTNESS, Constant.BEAUTY_EFFECT_DEFAULT_SMOOTHNESS, Constant.BEAUTY_EFFECT_DEFAULT_REDNESS); + enablePreProcessor(); } else { - worker().disablePreProcessor(); + disablePreProcessor(); } ImageView iv = (ImageView) view; @@ -415,16 +404,14 @@ public void onFilterClicked(View view) { @Override protected void deInitUIandEvent() { optionalDestroy(); - doLeaveChannel(); - event().removeEventHandler(this); - + removeEventHandler(this); mUidsList.clear(); } private void doLeaveChannel() { - worker().leaveChannel(config().mChannel); - worker().preview(false, null, 0); + leaveChannel(config().mChannel); + preview(false, null, 0); } public void onHangupClicked(View view) { @@ -585,37 +572,16 @@ public void run() { @Override public void onJoinChannelSuccess(String channel, final int uid, int elapsed) { log.debug("onJoinChannelSuccess " + channel + " " + (uid & 0xFFFFFFFFL) + " " + elapsed); - - runOnUiThread(new Runnable() { - @Override - public void run() { - if (isFinishing()) { - return; - } - - notifyMessageChanged(new Message(new User(0, null), "join " + channel + " success as " + (uid & 0xFFFFFFFFL) + " in " + elapsed + "ms")); - - SurfaceView local = mUidsList.remove(0); - - if (local == null) { - return; - } - - mUidsList.put(uid, local); - } - }); } @Override public void onUserOffline(int uid, int reason) { log.debug("onUserOffline " + (uid & 0xFFFFFFFFL) + " " + reason); - doRemoveRemoteUi(uid); } @Override public void onExtraCallback(final int type, final Object... data) { - runOnUiThread(new Runnable() { @Override public void run() { diff --git a/Group-Video/OpenVideoCall-Android/app/src/main/java/io/agora/openvcall/ui/MainActivity.java b/Group-Video/OpenVideoCall-Android/app/src/main/java/io/agora/openvcall/ui/MainActivity.java index 06dc9a31..bc4a3cf6 100644 --- a/Group-Video/OpenVideoCall-Android/app/src/main/java/io/agora/openvcall/ui/MainActivity.java +++ b/Group-Video/OpenVideoCall-Android/app/src/main/java/io/agora/openvcall/ui/MainActivity.java @@ -146,7 +146,7 @@ public void onClickDoNetworkTest(View view) { } @Override - public void workerThreadReady() { + public void permissionGranted() { } diff --git a/Group-Video/OpenVideoCall-Android/app/src/main/java/io/agora/openvcall/ui/NetworkTestActivity.java b/Group-Video/OpenVideoCall-Android/app/src/main/java/io/agora/openvcall/ui/NetworkTestActivity.java index 5022e23f..73ccce04 100644 --- a/Group-Video/OpenVideoCall-Android/app/src/main/java/io/agora/openvcall/ui/NetworkTestActivity.java +++ b/Group-Video/OpenVideoCall-Android/app/src/main/java/io/agora/openvcall/ui/NetworkTestActivity.java @@ -34,7 +34,7 @@ protected void onCreate(Bundle savedInstanceState) { @Override protected void initUIandEvent() { - event().addEventHandler(this); + addEventHandler(this); ((TextView) findViewById(R.id.ovc_page_title)).setText(R.string.label_network_testing); @@ -49,7 +49,7 @@ protected void initUIandEvent() { @Override protected void deInitUIandEvent() { rtcEngine().stopLastmileProbeTest(); - event().removeEventHandler(this); + removeEventHandler(this); } @Override diff --git a/Group-Video/OpenVideoCall-Android/app/src/main/res/values/strings_config.xml b/Group-Video/OpenVideoCall-Android/app/src/main/res/values/strings_config.xml index 639101d5..f9dc6680 100644 --- a/Group-Video/OpenVideoCall-Android/app/src/main/res/values/strings_config.xml +++ b/Group-Video/OpenVideoCall-Android/app/src/main/res/values/strings_config.xml @@ -9,7 +9,7 @@ <#YOUR APP ID#> - #YOUR ACCESS TOKEN# + <#YOUR ACCESS TOKEN#> AES-128-XTS diff --git a/Group-Video/OpenVideoCall-Android/ci.env.py b/Group-Video/OpenVideoCall-Android/ci.env.py index dfc7dbac..6a5d0528 100644 --- a/Group-Video/OpenVideoCall-Android/ci.env.py +++ b/Group-Video/OpenVideoCall-Android/ci.env.py @@ -5,13 +5,13 @@ def main(): - f = open("./app/build.gradle", 'r+') - content = f.read() - x = re.sub( - r'(dependencies {$)(.*)', r"\1\n implementation 'io.agora.rtc:full-sdk:2.4.1'\2", content, flags=re.M) - f.seek(0) - f.write(x) - f.truncate() +# f = open("./app/build.gradle", 'r+') +# content = f.read() +# x = re.sub( +# r'(dependencies {$)(.*)', r"\1\n implementation 'io.agora.rtc:full-sdk:2.4.1'\2", content, flags=re.M) +# f.seek(0) +# f.write(x) +# f.truncate() appId = "" if "AGORA_APP_ID" in os.environ: @@ -21,7 +21,7 @@ def main(): f = open("./app/src/main/res/values/strings_config.xml", 'r+') content = f.read() contentNew = re.sub(r'<#YOUR APP ID#>', appId, content) - contentNew = re.sub(r'#YOUR ACCESS TOKEN#', token, contentNew) + contentNew = re.sub(r'<#YOUR ACCESS TOKEN#>', token, contentNew) f.seek(0) f.write(contentNew) f.truncate() diff --git a/Group-Video/OpenVideoCall-Web/README.md b/Group-Video/OpenVideoCall-Web/README.md index fd6d8848..3f404789 100755 --- a/Group-Video/OpenVideoCall-Web/README.md +++ b/Group-Video/OpenVideoCall-Web/README.md @@ -25,10 +25,10 @@ To build and run the sample application, get an App ID: **Note:** Place the App ID/Token within single or double quotes. - ```javascript - export const APP_ID = "<#YOUR APP ID HERE#>"; + ```xml + export const APP_ID = <#YOUR APP ID#>; - // If you have not enabled app certificate, make sure to set the Token to null + // Assign Token to null if you have not enabled app certificate export const Token = "<#YOUR TEMP TOKEN HERE#>"; ``` @@ -57,8 +57,13 @@ To build and run the sample application, get an App ID: ## Resources -- You can find full API document at [Document Center](https://docs.agora.io/en/) -- You can file bugs about this demo at [issue](https://github.com/AgoraIO/Basic-Video-Call/issues) +- For potential issues, take a look at our [FAQ](https://docs.agora.io/cn/faq) first +- Dive into [Agora SDK Samples](https://github.com/AgoraIO) to see more tutorials +- Take a look at [Agora Use Case](https://github.com/AgoraIO-usecase) for more complicated real use case +- Repositories managed by developer communities can be found at [Agora Community](https://github.com/AgoraIO-Community) +- You can find full API documentation at [Document Center](https://docs.agora.io/en/) +- If you encounter problems during integration, you can ask question in [Stack Overflow](https://stackoverflow.com/questions/tagged/agora.io) +- You can file bugs about this sample at [issue](https://github.com/AgoraIO/Basic-Video-Call/issues) ## License diff --git a/Group-Video/OpenVideoCall-Web/README.yaml b/Group-Video/OpenVideoCall-Web/README.yaml deleted file mode 100644 index 83f24c8a..00000000 --- a/Group-Video/OpenVideoCall-Web/README.yaml +++ /dev/null @@ -1,40 +0,0 @@ -Meta: - name: Open Video Call for Web - # en or cn - lang: en - # | 代表这里是字符串 - description: | - This tutorial shows you how to quickly create an open video call using the Agora sample app. - -Prerequisites: - - Node.js 6.9.1+ - - A web server that supports SSL (https) - -QuickStart: - description: - This section shows you how to prepare, build, and run the sample application. - sections: - - title: Obtain an App ID - content: | - $_{APPID} - 5. Open the **src/utils/Settings.js** file. At the bottom of the file, replace `<#YOUR APP ID#>` with the App ID, and assign the token variable with the temp Access Token generated from dashboard. - - **Note:** Place the App ID/Token within single or double quotes. - - ```xml - export const APP_ID = <#YOUR APP ID#>; - - // Assign Token to null if you have not enabled app certificate - export const Token = "<#YOUR TEMP TOKEN HERE#>"; - ``` - - title: Install dependencies and integrate the Agora Video SDK - content: | - - $_{WEB_RUN} - -Resources: - document: https://docs.agora.io/en/ - issue: https://github.com/AgoraIO/Basic-Video-Call/issues - -License: - type: MIT \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Web/README.zh.md b/Group-Video/OpenVideoCall-Web/README.zh.md index 3d3cda0c..d4f1bf97 100644 --- a/Group-Video/OpenVideoCall-Web/README.zh.md +++ b/Group-Video/OpenVideoCall-Web/README.zh.md @@ -47,11 +47,13 @@ ## 联系我们 +- 如果你遇到了困难,可以先参阅[常见问题](https://docs.agora.io/cn/faq) +- 如果你想了解更多官方示例,可以参考[官方SDK示例](https://github.com/AgoraIO) +- 如果你想了解声网SDK在复杂场景下的应用,可以参考[官方场景案例](https://github.com/AgoraIO-usecase) +- 如果你想了解声网的一些社区开发者维护的项目,可以查看[社区](https://github.com/AgoraIO-Community) - 完整的 API 文档见 [文档中心](https://docs.agora.io/cn/) -- 如果在集成中遇到问题, 你可以到 [开发者社区](https://dev.agora.io/cn/) 提问 -- 如果有售前咨询问题, 可以拨打 400 632 6626,或加入官方Q群 12742516 提问 -- 如果需要售后技术支持, 你可以在 [Agora Dashboard](https://dashboard.agora.io) 提交工单 -- 如果发现了示例代码的 bug, 欢迎提交 [issue](https://github.com/AgoraIO/Basic-Video-Call/issues) +- 若遇到问题需要开发者帮助,你可以到 [开发者社区](https://rtcdeveloper.com/) 提问 +- 如果发现了示例代码的 bug,欢迎提交 [issue](https://github.com/AgoraIO/Basic-Video-Call/issues) ## 代码许可 diff --git a/Group-Video/OpenVideoCall-Web/README.zh.yaml b/Group-Video/OpenVideoCall-Web/README.zh.yaml deleted file mode 100644 index d68118a0..00000000 --- a/Group-Video/OpenVideoCall-Web/README.zh.yaml +++ /dev/null @@ -1,38 +0,0 @@ -Meta: - name: Open Video Call for Web - # en or cn - lang: cn - # | 代表这里是字符串 - description: | - 这个开源示例项目演示了如何快速集成 Agora 视频 SDK,实现多人视频通话。 - -Prerequisites: - - Node.js 6.9.1+ - - 支持SSL(https)的服务器 - -QuickStart: - description: - 这个段落主要讲解了如何编译和运行示例程序。 - sections: - - title: 创建Agora账号并获取AppId - content: | - $_{APPID} - 5. 打开 **src/utils/Settings.js** 文件。在文件的底部,将`<#YOUR APP ID#>`替换为您自己的App ID,然后将`<#YOUR TEMP TOKEN#>`替换为dashboard计算的Token。 - - **注意:** App ID是字符串类型,需要双引号或者单引号 - ```javascript - export const APP_ID = <#YOUR APP ID#>; - - // 如果你没有打开Token功能,token可以直接给null - export const Token = "<#YOUR TEMP TOKEN HERE#>"; - ``` - - title: 集成 Agora 视频 SDK - content: | - $_{WEB_RUN} - -Resources: - document: https://docs.agora.io/cn/ - issue: https://github.com/AgoraIO/Basic-Video-Call/issues - -License: - type: MIT \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Windows/.gitignore b/Group-Video/OpenVideoCall-Windows/.gitignore new file mode 100644 index 00000000..11892919 --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/.gitignore @@ -0,0 +1,12 @@ +Win32/ +sdk/ +debug/ +release/ +*.sdf +*.opensdf +*.suo +*.vcxproj +*.vcxproj.filters +*.vcxproj.user +*.ini +ui_* diff --git a/Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/ChineseSimplified.cpp b/Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/ChineseSimplified.cpp deleted file mode 100644 index 78da8e07..00000000 --- a/Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/ChineseSimplified.cpp +++ /dev/null @@ -1,73 +0,0 @@ -// ChineseSimplified.cpp : DLL Ӧóĵ -// - -#include "stdafx.h" -#include "ChineseSimplified.h" - - -// ǵһʾ -CHINESESIMPLIFIED_API LPCTSTR IDS_TITLE = _T("Open Video Call"); -CHINESESIMPLIFIED_API LPCTSTR IDS_LOGO_DESC = _T("AgoraƵͨ ʵʱ ı"); -CHINESESIMPLIFIED_API LPCTSTR IDS_LOGO_AGORAWEB = _T("agora.io"); - -CHINESESIMPLIFIED_API LPCTSTR IDS_CONTACT = _T("ֵ֧绰: "); -CHINESESIMPLIFIED_API LPCTSTR IDS_PHONENUMBER = _T("400 632 6626"); - -CHINESESIMPLIFIED_API LPCTSTR IDS_PRE_TITLE = _T("Slelct conference type"); -CHINESESIMPLIFIED_API LPCTSTR IDS_PRE_OPTDSC1 = _T("* Optimized calls have best performance but"); -CHINESESIMPLIFIED_API LPCTSTR IDS_PRE_OPTDSC2 = _T(" cannot be joined by web participants"); -CHINESESIMPLIFIED_API LPCTSTR IDS_PRE_WEBDSC1 = _T("* Web-compatible calls have goog performance"); -CHINESESIMPLIFIED_API LPCTSTR IDS_PRE_WEBDSC2 = _T(" and open to web participants"); -CHINESESIMPLIFIED_API LPCTSTR IDS_PRE_BTNOPT = _T("Optimized"); -CHINESESIMPLIFIED_API LPCTSTR IDS_PRE_BTNWEB = _T("Web-compatible"); - -CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_TITLE = _T(""); -CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_DSC1 = _T("ûƲ, 㽫Զ뵽û; ûҴ, 㽫"); -CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_DSC2 = _T("ԶýеĻ"); -// CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_DSC3 = _T(""); -// CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_DSC4 = _T("progress"); - -CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_BTBACK = _T(""); -CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_BTTEST = _T("豸"); -CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_BTJOIN = _T(""); - -CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_CHTIP = _T("Ƶ"); -CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_KEYTIP = _T("Կ"); - -CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_ENCTYPE = _T("EncType:"); -CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_AES128XTS = _T("aes-128"); -CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_AES128GCM = _T("aes-128-gcm"); -CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_AES128CCM = _T("aes-128-ccm"); -CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_AES128CTR = _T("aes-128-ctr"); -CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_AES256XTS = _T("aes-256"); -CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_AES256GCM = _T("aes-256-gcm"); -CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_AES256CCM = _T("aes-256-ccm"); -CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_AES256CTR = _T("aes-256-ctr"); - -CHINESESIMPLIFIED_API LPCTSTR IDS_SET_RESOLUTION = _T("ֱ"); -CHINESESIMPLIFIED_API LPCTSTR IDS_SET_MFR = _T("֡"); -CHINESESIMPLIFIED_API LPCTSTR IDS_SET_MR = _T(""); -CHINESESIMPLIFIED_API LPCTSTR IDS_SET_BTCONFIRM = _T("ȷ"); - -CHINESESIMPLIFIED_API LPCTSTR IDS_SET_CODEC = _T(""); -CHINESESIMPLIFIED_API LPCTSTR IDS_SET_SWAPWH = _T("߱Ȼ"); -CHINESESIMPLIFIED_API LPCTSTR IDS_SET_SAVESETTING = _T("浱ǰ"); - -CHINESESIMPLIFIED_API LPCTSTR IDS_DEVICE_AUDIOIN = _T("Ƶ:"); -CHINESESIMPLIFIED_API LPCTSTR IDS_DEVICE_AUDIOOUT = _T("Ƶ:"); -CHINESESIMPLIFIED_API LPCTSTR IDS_DEVICE_CAMERA = _T("ͷ:"); -CHINESESIMPLIFIED_API LPCTSTR IDS_DEVICE_VOLUME = _T(""); -CHINESESIMPLIFIED_API LPCTSTR IDS_DEVICE_BTNTEST = _T(""); -CHINESESIMPLIFIED_API LPCTSTR IDS_DEVICE_BTNTESTOFF = _T("ֹͣ"); -CHINESESIMPLIFIED_API LPCTSTR IDS_DEVICE_CANCEL = _T("ȡ"); -CHINESESIMPLIFIED_API LPCTSTR IDS_DEVICE_CONFIRM = _T("ȷ"); - -CHINESESIMPLIFIED_API LPCTSTR IDS_VIDEO_SCRSHARE = _T("Ļ"); -CHINESESIMPLIFIED_API LPCTSTR IDS_VIDEO_WNDSHARE = _T("ڹ"); - -CHINESESIMPLIFIED_API LPCTSTR IDS_VIDEO_WBHOST = _T("ģʽ"); -CHINESESIMPLIFIED_API LPCTSTR IDS_VIDEO_WBGUEST = _T("ģʽ"); - -CHINESESIMPLIFIED_API LPCTSTR IDS_VIDEO_MOREINFO = _T("ƵϢ"); -CHINESESIMPLIFIED_API LPCTSTR IDS_VIDEO_MOREDEVICE = _T("豸"); -CHINESESIMPLIFIED_API LPCTSTR IDS_VIDEO_MOREFILTER = _T("˾"); \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/ChineseSimplified.h b/Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/ChineseSimplified.h deleted file mode 100644 index 811549e9..00000000 --- a/Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/ChineseSimplified.h +++ /dev/null @@ -1,80 +0,0 @@ -// ifdef Ǵʹ DLL 򵥵 -// ı׼ DLL еļ϶ CHINESESIMPLIFIED_EXPORTS -// űġʹô DLL -// κĿϲӦ˷šԴļаļκĿὫ -// CHINESESIMPLIFIED_API ΪǴ DLL ģ DLL ô˺궨 -// ΪDZġ -#ifdef CHINESESIMPLIFIED_EXPORTS -#define CHINESESIMPLIFIED_API __declspec(dllexport) -#else -#define CHINESESIMPLIFIED_API __declspec(dllimport) -#endif - -extern CHINESESIMPLIFIED_API LPCTSTR IDS_TITLE; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_LOGO_DESC; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_LOGO_AGORAWEB; - -extern CHINESESIMPLIFIED_API LPCTSTR IDS_CONTACT; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_PHONENUMBER; - -extern CHINESESIMPLIFIED_API LPCTSTR IDS_PRE_TITLE; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_PRE_OPTDSC1; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_PRE_OPTDSC2; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_PRE_WEBDSC1; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_PRE_WEBDSC2; - -extern CHINESESIMPLIFIED_API LPCTSTR IDS_PRE_BTNOPT; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_PRE_BTNWEB; - -extern CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_TITLE; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_DSC1; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_DSC2; -//extern CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_DSC3; -//extern CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_DSC4; - -extern CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_BTBACK; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_BTTEST; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_BTJOIN; - -extern CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_CHTIP; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_KEYTIP; - -extern CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_ENCTYPE; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_AES128XTS; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_AES128GCM; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_AES128CCM; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_AES128CTR; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_AES256XTS; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_AES256GCM; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_AES256CCM; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_CHN_AES256CTR; - -extern CHINESESIMPLIFIED_API LPCTSTR IDS_SET_RESOLUTION; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_SET_MFR; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_SET_MR; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_SET_BTCONFIRM; - -extern CHINESESIMPLIFIED_API LPCTSTR IDS_SET_CODEC; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_SET_SWAPWH; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_SET_SAVESETTING; - -extern CHINESESIMPLIFIED_API LPCTSTR IDS_DEVICE_AUDIOIN; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_DEVICE_AUDIOOUT; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_DEVICE_CAMERA; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_DEVICE_VOLUME; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_DEVICE_BTNTEST; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_DEVICE_BTNTESTOFF; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_DEVICE_CANCEL; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_DEVICE_CONFIRM; - -extern CHINESESIMPLIFIED_API LPCTSTR IDS_VIDEO_SCRSHARE; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_VIDEO_WNDSHARE; - -extern CHINESESIMPLIFIED_API LPCTSTR IDS_VIDEO_WBHOST; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_VIDEO_WBGUEST; - -extern CHINESESIMPLIFIED_API LPCTSTR IDS_VIDEO_MOREINFO; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_VIDEO_MOREDEVICE; -extern CHINESESIMPLIFIED_API LPCTSTR IDS_VIDEO_MOREFILTER; - - diff --git a/Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/ChineseSimplified.vcxproj b/Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/ChineseSimplified.vcxproj deleted file mode 100644 index 794937d5..00000000 --- a/Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/ChineseSimplified.vcxproj +++ /dev/null @@ -1,190 +0,0 @@ - - - - - Debug - Win32 - - - Debug - x64 - - - Release - Win32 - - - Release - x64 - - - - {898289D0-0D57-4B8E-97AE-013114F85DE9} - Win32Proj - ChineseSimplified - - - - DynamicLibrary - true - v120 - Unicode - - - DynamicLibrary - true - v120 - Unicode - - - DynamicLibrary - false - v120_xp - true - Unicode - - - DynamicLibrary - false - v120_xp - true - Unicode - - - - - - - - - - - - - - - - - - - true - $(SolutionDir)$(Configuration)\Language\ - - - true - $(SolutionDir)\$(Configuration)\Language\ - $(Configuration)\ - - - false - $(SolutionDir)$(Configuration)\Language\ - - - false - $(SolutionDir)\$(Configuration)\Language\ - $(Configuration)\ - - - - Use - Level3 - Disabled - WIN32;_DEBUG;_WINDOWS;_USRDLL;CHINESESIMPLIFIED_EXPORTS;%(PreprocessorDefinitions) - true - - - Windows - true - Source.def - - - - - Use - Level3 - Disabled - WIN32;_DEBUG;_WINDOWS;_USRDLL;CHINESESIMPLIFIED_EXPORTS;%(PreprocessorDefinitions) - true - - - Windows - true - Source.def - - - - - Level3 - Use - MaxSpeed - true - true - WIN32;NDEBUG;_WINDOWS;_USRDLL;CHINESESIMPLIFIED_EXPORTS;%(PreprocessorDefinitions) - true - MultiThreaded - - - Windows - true - true - true - Source.def - - - - - Level3 - Use - MaxSpeed - true - true - WIN32;NDEBUG;_WINDOWS;_USRDLL;CHINESESIMPLIFIED_EXPORTS;%(PreprocessorDefinitions) - true - MultiThreaded - - - Windows - true - true - true - Source.def - - - - - - - - - - - - - - false - false - - - - - false - false - - - - - - - Create - Create - Create - Create - - - - - - - - - \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/ChineseSimplified.vcxproj.filters b/Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/ChineseSimplified.vcxproj.filters deleted file mode 100644 index 11e14998..00000000 --- a/Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/ChineseSimplified.vcxproj.filters +++ /dev/null @@ -1,47 +0,0 @@ - - - - - {4FC737F1-C7A5-4376-A066-2A32D752A2FF} - cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx - - - {93995380-89BD-4b04-88EB-625FBE52EBFB} - h;hh;hpp;hxx;hm;inl;inc;xsd - - - {67DA6AB6-F800-4c08-8B7A-83BB121AAD01} - rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms - - - - - - - - 头文件 - - - 头文件 - - - 头文件 - - - - - 源文件 - - - 源文件 - - - 源文件 - - - - - 源文件 - - - \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/Source.def b/Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/Source.def deleted file mode 100644 index ebb6cb8a..00000000 --- a/Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/Source.def +++ /dev/null @@ -1,66 +0,0 @@ -LIBRARY -EXPORTS - -IDS_TITLE DATA; - -IDS_LOGO_DESC DATA; -IDS_LOGO_AGORAWEB DATA; -IDS_CONTACT DATA; -IDS_PHONENUMBER DATA; - -IDS_PRE_TITLE DATA; -IDS_PRE_OPTDSC1 DATA; -IDS_PRE_OPTDSC2 DATA; -IDS_PRE_WEBDSC1 DATA; -IDS_PRE_WEBDSC2 DATA; - -IDS_PRE_BTNOPT DATA; -IDS_PRE_BTNWEB DATA; - -IDS_CHN_TITLE DATA; -IDS_CHN_DSC1 DATA; -IDS_CHN_DSC2 DATA; - -IDS_CHN_BTBACK DATA; -IDS_CHN_BTTEST DATA; -IDS_CHN_BTJOIN DATA; - -IDS_CHN_CHTIP DATA; -IDS_CHN_KEYTIP DATA; -IDS_CHN_ENCTYPE DATA; - -IDS_CHN_AES128XTS DATA; -IDS_CHN_AES128GCM DATA; -IDS_CHN_AES128CCM DATA; -IDS_CHN_AES128CTR DATA; -IDS_CHN_AES256XTS DATA; -IDS_CHN_AES256GCM DATA; -IDS_CHN_AES256CCM DATA; -IDS_CHN_AES256CTR DATA; - -IDS_SET_RESOLUTION DATA; -IDS_SET_MFR DATA; -IDS_SET_MR DATA; -IDS_SET_BTCONFIRM DATA; - -IDS_SET_CODEC DATA; -IDS_SET_SWAPWH DATA; -IDS_SET_SAVESETTING DATA; - -IDS_DEVICE_AUDIOIN DATA; -IDS_DEVICE_AUDIOOUT DATA; -IDS_DEVICE_CAMERA DATA; -IDS_DEVICE_VOLUME DATA; -IDS_DEVICE_BTNTEST DATA; -IDS_DEVICE_BTNTESTOFF DATA; -IDS_DEVICE_CANCEL DATA; -IDS_DEVICE_CONFIRM DATA; - -IDS_VIDEO_SCRSHARE DATA; -IDS_VIDEO_WNDSHARE DATA; -IDS_VIDEO_WBHOST DATA; -IDS_VIDEO_WBGUEST DATA; - -IDS_VIDEO_MOREINFO DATA; -IDS_VIDEO_MOREDEVICE DATA; -IDS_VIDEO_MOREFILTER DATA;LIBRARY diff --git a/Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/dllmain.cpp b/Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/dllmain.cpp deleted file mode 100644 index 260abc6d..00000000 --- a/Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/dllmain.cpp +++ /dev/null @@ -1,19 +0,0 @@ -// dllmain.cpp : DLL Ӧóڵ㡣 -#include "stdafx.h" - -BOOL APIENTRY DllMain( HMODULE hModule, - DWORD ul_reason_for_call, - LPVOID lpReserved - ) -{ - switch (ul_reason_for_call) - { - case DLL_PROCESS_ATTACH: - case DLL_THREAD_ATTACH: - case DLL_THREAD_DETACH: - case DLL_PROCESS_DETACH: - break; - } - return TRUE; -} - diff --git a/Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/stdafx.cpp b/Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/stdafx.cpp deleted file mode 100644 index fd46dc5b..00000000 --- a/Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/stdafx.cpp +++ /dev/null @@ -1,8 +0,0 @@ -// stdafx.cpp : ֻ׼ļԴļ -// ChineseSimplified.pch ΪԤͷ -// stdafx.obj ԤϢ - -#include "stdafx.h" - -// TODO: STDAFX.H -// κĸͷļڴļ diff --git a/Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/stdafx.h b/Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/stdafx.h deleted file mode 100644 index 254f1ef8..00000000 --- a/Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/stdafx.h +++ /dev/null @@ -1,14 +0,0 @@ -// stdafx.h : ׼ϵͳļİļ -// Ǿʹõĵ -// ضĿİļ -// - -#pragma once - -#include "targetver.h" - -#define WIN32_LEAN_AND_MEAN // Windows ͷļųʹõϢ -// Windows ͷļ: -#include -#include -// TODO: ڴ˴óҪͷļ diff --git a/Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/targetver.h b/Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/targetver.h deleted file mode 100644 index 7a7d2c83..00000000 --- a/Group-Video/OpenVideoCall-Windows/Language/ChineseSimplified/targetver.h +++ /dev/null @@ -1,8 +0,0 @@ -#pragma once - -// SDKDDKVer.h õ߰汾 Windows ƽ̨ - -// ҪΪǰ Windows ƽ̨Ӧó WinSDKVer.h -// WIN32_WINNT ΪҪֵ֧ƽ̨Ȼٰ SDKDDKVer.h - -#include diff --git a/Group-Video/OpenVideoCall-Windows/Language/English/English.cpp b/Group-Video/OpenVideoCall-Windows/Language/English/English.cpp deleted file mode 100644 index ecc56032..00000000 --- a/Group-Video/OpenVideoCall-Windows/Language/English/English.cpp +++ /dev/null @@ -1,73 +0,0 @@ -// English.cpp : DLL Ӧóĵ -// - -#include "stdafx.h" -#include "English.h" - - - -ENGLISH_API LPCTSTR IDS_TITLE = _T("Open Video Call"); -ENGLISH_API LPCTSTR IDS_LOGO_DESC = _T("Powering Real-Time Communications"); -ENGLISH_API LPCTSTR IDS_LOGO_AGORAWEB = _T("agora.io"); - -ENGLISH_API LPCTSTR IDS_CONTACT = _T("Contact support: "); -ENGLISH_API LPCTSTR IDS_PHONENUMBER = _T("400 632 6626"); - -ENGLISH_API LPCTSTR IDS_PRE_TITLE = _T("Slelct conference type"); -ENGLISH_API LPCTSTR IDS_PRE_OPTDSC1 = _T("* Optimized calls have best performance but"); -ENGLISH_API LPCTSTR IDS_PRE_OPTDSC2 = _T(" cannot be joined by web participants"); -ENGLISH_API LPCTSTR IDS_PRE_WEBDSC1 = _T("* Web-compatible calls have goog performance"); -ENGLISH_API LPCTSTR IDS_PRE_WEBDSC2 = _T(" and open to web participants"); -ENGLISH_API LPCTSTR IDS_PRE_BTNOPT = _T("Optimized"); -ENGLISH_API LPCTSTR IDS_PRE_BTNWEB = _T("Web-compatible"); - -ENGLISH_API LPCTSTR IDS_CHN_TITLE = _T("Enter a conference room name"); -ENGLISH_API LPCTSTR IDS_CHN_DSC1 = _T("if you are the first person to specify this name,the room will be created and you will be"); -ENGLISH_API LPCTSTR IDS_CHN_DSC2 = _T("placed in it.if it has already been created you will join the conference in progress"); -// ENGLISH_API LPCTSTR IDS_CHN_DSC3 = _T(""); -// ENGLISH_API LPCTSTR IDS_CHN_DSC4 = _T("progress"); - -ENGLISH_API LPCTSTR IDS_CHN_BTBACK = _T("Back"); -ENGLISH_API LPCTSTR IDS_CHN_BTTEST = _T("Test"); -ENGLISH_API LPCTSTR IDS_CHN_BTJOIN = _T("Join"); - -ENGLISH_API LPCTSTR IDS_CHN_CHTIP = _T("ChannelName"); -ENGLISH_API LPCTSTR IDS_CHN_KEYTIP = _T("EncryptionKey"); - -ENGLISH_API LPCTSTR IDS_CHN_ENCTYPE = _T("EncType:"); -ENGLISH_API LPCTSTR IDS_CHN_AES128XTS = _T("aes-128"); -ENGLISH_API LPCTSTR IDS_CHN_AES128GCM = _T("aes-128-gcm"); -ENGLISH_API LPCTSTR IDS_CHN_AES128CCM = _T("aes-128-ccm"); -ENGLISH_API LPCTSTR IDS_CHN_AES128CTR = _T("aes-128-ctr"); -ENGLISH_API LPCTSTR IDS_CHN_AES256XTS = _T("aes-256"); -ENGLISH_API LPCTSTR IDS_CHN_AES256GCM = _T("aes-256-gcm"); -ENGLISH_API LPCTSTR IDS_CHN_AES256CCM = _T("aes-256-ccm"); -ENGLISH_API LPCTSTR IDS_CHN_AES256CTR = _T("aes-256-ctr"); - -ENGLISH_API LPCTSTR IDS_SET_RESOLUTION = _T("Resolution"); -ENGLISH_API LPCTSTR IDS_SET_MFR = _T("Max Frame rate"); -ENGLISH_API LPCTSTR IDS_SET_MR = _T("Max rate"); -ENGLISH_API LPCTSTR IDS_SET_BTCONFIRM = _T("Confirm"); - -ENGLISH_API LPCTSTR IDS_SET_CODEC = _T("Codec"); -ENGLISH_API LPCTSTR IDS_SET_SWAPWH = _T("swap wide and height"); -ENGLISH_API LPCTSTR IDS_SET_SAVESETTING = _T("save the settings"); - -ENGLISH_API LPCTSTR IDS_DEVICE_AUDIOIN = _T("Input Device:"); -ENGLISH_API LPCTSTR IDS_DEVICE_AUDIOOUT = _T("Output Device:"); -ENGLISH_API LPCTSTR IDS_DEVICE_CAMERA = _T("Camera:"); -ENGLISH_API LPCTSTR IDS_DEVICE_VOLUME = _T("Volume"); -ENGLISH_API LPCTSTR IDS_DEVICE_BTNTEST = _T("test"); -ENGLISH_API LPCTSTR IDS_DEVICE_BTNTESTOFF = _T("Stop"); -ENGLISH_API LPCTSTR IDS_DEVICE_CANCEL = _T("Cancel"); -ENGLISH_API LPCTSTR IDS_DEVICE_CONFIRM = _T("Confirm"); - -ENGLISH_API LPCTSTR IDS_VIDEO_SCRSHARE = _T("Screen Share"); -ENGLISH_API LPCTSTR IDS_VIDEO_WNDSHARE = _T("Window Share"); - -ENGLISH_API LPCTSTR IDS_VIDEO_WBHOST = _T("Host Mode"); -ENGLISH_API LPCTSTR IDS_VIDEO_WBGUEST = _T("Guest Mode"); - -ENGLISH_API LPCTSTR IDS_VIDEO_MOREINFO = _T("Video Info"); -ENGLISH_API LPCTSTR IDS_VIDEO_MOREDEVICE = _T("Device"); -ENGLISH_API LPCTSTR IDS_VIDEO_MOREFILTER = _T("Video Filter"); \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Windows/Language/English/English.h b/Group-Video/OpenVideoCall-Windows/Language/English/English.h deleted file mode 100644 index 720907e3..00000000 --- a/Group-Video/OpenVideoCall-Windows/Language/English/English.h +++ /dev/null @@ -1,79 +0,0 @@ -// ifdef Ǵʹ DLL 򵥵 -// ı׼ DLL еļ϶ ENGLISH_EXPORTS -// űġʹô DLL -// κĿϲӦ˷šԴļаļκĿὫ -// ENGLISH_API ΪǴ DLL ģ DLL ô˺궨 -// ΪDZġ -#ifdef ENGLISH_EXPORTS -#define ENGLISH_API __declspec(dllexport) -#else -#define ENGLISH_API __declspec(dllimport) -#endif - - -extern ENGLISH_API LPCTSTR IDS_TITLE; -extern ENGLISH_API LPCTSTR IDS_LOGO_DESC; -extern ENGLISH_API LPCTSTR IDS_LOGO_AGORAWEB; - -extern ENGLISH_API LPCTSTR IDS_CONTACT; -extern ENGLISH_API LPCTSTR IDS_PHONENUMBER; - -extern ENGLISH_API LPCTSTR IDS_PRE_TITLE; -extern ENGLISH_API LPCTSTR IDS_PRE_OPTDSC1; -extern ENGLISH_API LPCTSTR IDS_PRE_OPTDSC2; -extern ENGLISH_API LPCTSTR IDS_PRE_WEBDSC1; -extern ENGLISH_API LPCTSTR IDS_PRE_WEBDSC2; - -extern ENGLISH_API LPCTSTR IDS_PRE_BTNOPT; -extern ENGLISH_API LPCTSTR IDS_PRE_BTNWEB; - -extern ENGLISH_API LPCTSTR IDS_CHN_TITLE; -extern ENGLISH_API LPCTSTR IDS_CHN_DSC1; -extern ENGLISH_API LPCTSTR IDS_CHN_DSC2; -//extern ENGLISH_API LPCTSTR IDS_CHN_DSC3; -//extern ENGLISH_API LPCTSTR IDS_CHN_DSC4; - -extern ENGLISH_API LPCTSTR IDS_CHN_BTBACK; -extern ENGLISH_API LPCTSTR IDS_CHN_BTTEST; -extern ENGLISH_API LPCTSTR IDS_CHN_BTJOIN; - -extern ENGLISH_API LPCTSTR IDS_CHN_CHTIP; -extern ENGLISH_API LPCTSTR IDS_CHN_KEYTIP; - -extern ENGLISH_API LPCTSTR IDS_CHN_ENCTYPE; -extern ENGLISH_API LPCTSTR IDS_CHN_AES128XTS; -extern ENGLISH_API LPCTSTR IDS_CHN_AES128GCM; -extern ENGLISH_API LPCTSTR IDS_CHN_AES128CCM; -extern ENGLISH_API LPCTSTR IDS_CHN_AES128CTR; -extern ENGLISH_API LPCTSTR IDS_CHN_AES256XTS; -extern ENGLISH_API LPCTSTR IDS_CHN_AES256GCM; -extern ENGLISH_API LPCTSTR IDS_CHN_AES256CCM; -extern ENGLISH_API LPCTSTR IDS_CHN_AES256CTR; - -extern ENGLISH_API LPCTSTR IDS_SET_RESOLUTION; -extern ENGLISH_API LPCTSTR IDS_SET_MFR; -extern ENGLISH_API LPCTSTR IDS_SET_MR; -extern ENGLISH_API LPCTSTR IDS_SET_BTCONFIRM; - -extern ENGLISH_API LPCTSTR IDS_SET_CODEC; -extern ENGLISH_API LPCTSTR IDS_SET_SWAPWH; -extern ENGLISH_API LPCTSTR IDS_SET_SAVESETTING; - -extern ENGLISH_API LPCTSTR IDS_DEVICE_AUDIOIN; -extern ENGLISH_API LPCTSTR IDS_DEVICE_AUDIOOUT; -extern ENGLISH_API LPCTSTR IDS_DEVICE_CAMERA; -extern ENGLISH_API LPCTSTR IDS_DEVICE_VOLUME; -extern ENGLISH_API LPCTSTR IDS_DEVICE_BTNTEST; -extern ENGLISH_API LPCTSTR IDS_DEVICE_BTNTESTOFF; -extern ENGLISH_API LPCTSTR IDS_DEVICE_CANCEL; -extern ENGLISH_API LPCTSTR IDS_DEVICE_CONFIRM; - -extern ENGLISH_API LPCTSTR IDS_VIDEO_SCRSHARE; -extern ENGLISH_API LPCTSTR IDS_VIDEO_WNDSHARE; - -extern ENGLISH_API LPCTSTR IDS_VIDEO_WBHOST; -extern ENGLISH_API LPCTSTR IDS_VIDEO_WBGUEST; - -extern ENGLISH_API LPCTSTR IDS_VIDEO_MOREINFO; -extern ENGLISH_API LPCTSTR IDS_VIDEO_MOREDEVICE; -extern ENGLISH_API LPCTSTR IDS_VIDEO_MOREFILTER; diff --git a/Group-Video/OpenVideoCall-Windows/Language/English/English.vcxproj b/Group-Video/OpenVideoCall-Windows/Language/English/English.vcxproj deleted file mode 100644 index b0d849c1..00000000 --- a/Group-Video/OpenVideoCall-Windows/Language/English/English.vcxproj +++ /dev/null @@ -1,190 +0,0 @@ - - - - - Debug - Win32 - - - Debug - x64 - - - Release - Win32 - - - Release - x64 - - - - {DE1D9363-5455-4448-8D69-D22BE47F5A82} - Win32Proj - English - - - - DynamicLibrary - true - v120 - Unicode - - - DynamicLibrary - true - v120 - Unicode - - - DynamicLibrary - false - v120_xp - true - Unicode - - - DynamicLibrary - false - v120_xp - true - Unicode - - - - - - - - - - - - - - - - - - - true - $(SolutionDir)$(Configuration)\Language\ - - - true - $(SolutionDir)\$(Configuration)\Language\ - $(Configuration)\ - - - false - $(SolutionDir)$(Configuration)\Language\ - - - false - $(SolutionDir)\$(Configuration)\Language\ - $(Configuration)\ - - - - Use - Level3 - Disabled - WIN32;_DEBUG;_WINDOWS;_USRDLL;ENGLISH_EXPORTS;%(PreprocessorDefinitions) - true - - - Windows - true - Source.def - - - - - Use - Level3 - Disabled - WIN32;_DEBUG;_WINDOWS;_USRDLL;ENGLISH_EXPORTS;%(PreprocessorDefinitions) - true - - - Windows - true - Source.def - - - - - Level3 - Use - MaxSpeed - true - true - WIN32;NDEBUG;_WINDOWS;_USRDLL;ENGLISH_EXPORTS;%(PreprocessorDefinitions) - true - MultiThreaded - - - Windows - true - true - true - Source.def - - - - - Level3 - Use - MaxSpeed - true - true - WIN32;NDEBUG;_WINDOWS;_USRDLL;ENGLISH_EXPORTS;%(PreprocessorDefinitions) - true - MultiThreaded - - - Windows - true - true - true - Source.def - - - - - - - - - - - - - false - false - - - - - false - false - - - - - - - - Create - Create - Create - Create - - - - - - - - - \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Windows/Language/English/English.vcxproj.filters b/Group-Video/OpenVideoCall-Windows/Language/English/English.vcxproj.filters deleted file mode 100644 index 9b69fb3a..00000000 --- a/Group-Video/OpenVideoCall-Windows/Language/English/English.vcxproj.filters +++ /dev/null @@ -1,47 +0,0 @@ - - - - - {4FC737F1-C7A5-4376-A066-2A32D752A2FF} - cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx - - - {93995380-89BD-4b04-88EB-625FBE52EBFB} - h;hh;hpp;hxx;hm;inl;inc;xsd - - - {67DA6AB6-F800-4c08-8B7A-83BB121AAD01} - rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms - - - - - - - - 头文件 - - - 头文件 - - - 头文件 - - - - - 源文件 - - - 源文件 - - - 源文件 - - - - - 源文件 - - - \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Windows/Language/English/Source.def b/Group-Video/OpenVideoCall-Windows/Language/English/Source.def deleted file mode 100644 index d1e513ec..00000000 --- a/Group-Video/OpenVideoCall-Windows/Language/English/Source.def +++ /dev/null @@ -1,66 +0,0 @@ -LIBRARY -EXPORTS - -IDS_TITLE DATA; - -IDS_LOGO_DESC DATA; -IDS_LOGO_AGORAWEB DATA; -IDS_CONTACT DATA; -IDS_PHONENUMBER DATA; - -IDS_PRE_TITLE DATA; -IDS_PRE_OPTDSC1 DATA; -IDS_PRE_OPTDSC2 DATA; -IDS_PRE_WEBDSC1 DATA; -IDS_PRE_WEBDSC2 DATA; - -IDS_PRE_BTNOPT DATA; -IDS_PRE_BTNWEB DATA; - -IDS_CHN_TITLE DATA; -IDS_CHN_DSC1 DATA; -IDS_CHN_DSC2 DATA; - -IDS_CHN_BTBACK DATA; -IDS_CHN_BTTEST DATA; -IDS_CHN_BTJOIN DATA; - -IDS_CHN_CHTIP DATA; -IDS_CHN_KEYTIP DATA; -IDS_CHN_ENCTYPE DATA; - -IDS_CHN_AES128XTS DATA; -IDS_CHN_AES128GCM DATA; -IDS_CHN_AES128CCM DATA; -IDS_CHN_AES128CTR DATA; -IDS_CHN_AES256XTS DATA; -IDS_CHN_AES256GCM DATA; -IDS_CHN_AES256CCM DATA; -IDS_CHN_AES256CTR DATA; - -IDS_SET_RESOLUTION DATA; -IDS_SET_MFR DATA; -IDS_SET_MR DATA; -IDS_SET_BTCONFIRM DATA; - -IDS_SET_CODEC DATA; -IDS_SET_SWAPWH DATA; -IDS_SET_SAVESETTING DATA; - -IDS_DEVICE_AUDIOIN DATA; -IDS_DEVICE_AUDIOOUT DATA; -IDS_DEVICE_CAMERA DATA; -IDS_DEVICE_VOLUME DATA; -IDS_DEVICE_BTNTEST DATA; -IDS_DEVICE_BTNTESTOFF DATA; -IDS_DEVICE_CANCEL DATA; -IDS_DEVICE_CONFIRM DATA; - -IDS_VIDEO_SCRSHARE DATA; -IDS_VIDEO_WNDSHARE DATA; -IDS_VIDEO_WBHOST DATA; -IDS_VIDEO_WBGUEST DATA; - -IDS_VIDEO_MOREINFO DATA; -IDS_VIDEO_MOREDEVICE DATA; -IDS_VIDEO_MOREFILTER DATA; \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Windows/Language/English/dllmain.cpp b/Group-Video/OpenVideoCall-Windows/Language/English/dllmain.cpp deleted file mode 100644 index 260abc6d..00000000 --- a/Group-Video/OpenVideoCall-Windows/Language/English/dllmain.cpp +++ /dev/null @@ -1,19 +0,0 @@ -// dllmain.cpp : DLL Ӧóڵ㡣 -#include "stdafx.h" - -BOOL APIENTRY DllMain( HMODULE hModule, - DWORD ul_reason_for_call, - LPVOID lpReserved - ) -{ - switch (ul_reason_for_call) - { - case DLL_PROCESS_ATTACH: - case DLL_THREAD_ATTACH: - case DLL_THREAD_DETACH: - case DLL_PROCESS_DETACH: - break; - } - return TRUE; -} - diff --git a/Group-Video/OpenVideoCall-Windows/Language/English/stdafx.cpp b/Group-Video/OpenVideoCall-Windows/Language/English/stdafx.cpp deleted file mode 100644 index cfb88915..00000000 --- a/Group-Video/OpenVideoCall-Windows/Language/English/stdafx.cpp +++ /dev/null @@ -1,8 +0,0 @@ -// stdafx.cpp : ֻ׼ļԴļ -// English.pch ΪԤͷ -// stdafx.obj ԤϢ - -#include "stdafx.h" - -// TODO: STDAFX.H -// κĸͷļڴļ diff --git a/Group-Video/OpenVideoCall-Windows/Language/English/stdafx.h b/Group-Video/OpenVideoCall-Windows/Language/English/stdafx.h deleted file mode 100644 index 644ba2c0..00000000 --- a/Group-Video/OpenVideoCall-Windows/Language/English/stdafx.h +++ /dev/null @@ -1,16 +0,0 @@ -// stdafx.h : ׼ϵͳļİļ -// Ǿʹõĵ -// ضĿİļ -// - -#pragma once - -#include "targetver.h" - -#define WIN32_LEAN_AND_MEAN // Windows ͷļųʹõϢ -// Windows ͷļ: -#include -#include - - -// TODO: ڴ˴óҪͷļ diff --git a/Group-Video/OpenVideoCall-Windows/Language/English/targetver.h b/Group-Video/OpenVideoCall-Windows/Language/English/targetver.h deleted file mode 100644 index 7a7d2c83..00000000 --- a/Group-Video/OpenVideoCall-Windows/Language/English/targetver.h +++ /dev/null @@ -1,8 +0,0 @@ -#pragma once - -// SDKDDKVer.h õ߰汾 Windows ƽ̨ - -// ҪΪǰ Windows ƽ̨Ӧó WinSDKVer.h -// WIN32_WINNT ΪҪֵ֧ƽ̨Ȼٰ SDKDDKVer.h - -#include diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall.pro b/Group-Video/OpenVideoCall-Windows/OpenVideoCall.pro new file mode 100644 index 00000000..704c0013 --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/OpenVideoCall.pro @@ -0,0 +1,76 @@ +#------------------------------------------------- +# +# Project created by QtCreator 2019-09-24T10:52:31 +# +#------------------------------------------------- + +QT += core gui quickwidgets + +greaterThan(QT_MAJOR_VERSION, 4): QT += widgets + +TARGET = OpenVideoCall +TEMPLATE = app + + +SOURCES += main.cpp \ + agoraconfig.cpp \ + openvideocall.cpp \ + avdevice.cpp \ + agoraobject.cpp \ + nettesting.cpp \ + nettestresult.cpp \ + nettestdetail.cpp \ + agorawindowmanager.cpp \ + enterroom.cpp \ + inroom.cpp + +HEADERS += \ + agoraconfig.h \ + openvideocall.h \ + avdevice.h \ + agoraobject.h \ + nettesting.h \ + nettestresult.h \ + nettestdetail.h \ + agorawindowmanager.h \ + enterroom.h \ + inroom.h + +FORMS += \ + openvideocall.ui \ + avdevice.ui \ + nettesting.ui \ + nettestresult.ui \ + nettestdetail.ui \ + enterroom.ui \ + inroom.ui + +RESOURCES += \ + openvideocall.qrc + +RC_FILE = openvideocall.rc + +DISTFILES += \ + uiresource/OVC-win-more users.jpg \ + uiresource/icon-back hover.png \ + uiresource/icon-camera hover.png \ + uiresource/icon-camera off.png \ + uiresource/icon-close hover.png \ + uiresource/icon-hang up hover.png \ + uiresource/icon-hang up.png \ + uiresource/icon-micorophone hover.png \ + uiresource/icon-micorophone off.png \ + uiresource/icon-setting hover.png \ + openvideocall.rc + +win32: { +INCLUDEPATH += $$PWD/sdk/include +LIBS += -L$$PWD/sdk/lib/ -lagora_rtc_sdk +LIBS += User32.LIB +} + +win64: { +INCLUDEPATH += $$PWD/sdk/include +LIBS += -L$$PWD/sdk/lib/ -lagora_rtc_sdk +LIBS += User32.LIB +} diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall.sln b/Group-Video/OpenVideoCall-Windows/OpenVideoCall.sln deleted file mode 100644 index b4b1f5ff..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall.sln +++ /dev/null @@ -1,58 +0,0 @@ - -Microsoft Visual Studio Solution File, Format Version 12.00 -# Visual Studio 2013 -VisualStudioVersion = 12.0.40629.0 -MinimumVisualStudioVersion = 10.0.40219.1 -Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "OpenVideoCall", "OpenVideoCall\OpenVideoCall.vcxproj", "{26AF88DC-1933-4A1B-9991-21DF11DCE388}" - ProjectSection(ProjectDependencies) = postProject - {DE1D9363-5455-4448-8D69-D22BE47F5A82} = {DE1D9363-5455-4448-8D69-D22BE47F5A82} - {898289D0-0D57-4B8E-97AE-013114F85DE9} = {898289D0-0D57-4B8E-97AE-013114F85DE9} - EndProjectSection -EndProject -Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Language", "Language", "{4E3673B0-1BE6-41B7-9060-17A0B272CF19}" -EndProject -Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "English", "Language\English\English.vcxproj", "{DE1D9363-5455-4448-8D69-D22BE47F5A82}" -EndProject -Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "ChineseSimplified", "Language\ChineseSimplified\ChineseSimplified.vcxproj", "{898289D0-0D57-4B8E-97AE-013114F85DE9}" -EndProject -Global - GlobalSection(SolutionConfigurationPlatforms) = preSolution - Debug|Win32 = Debug|Win32 - Debug|x64 = Debug|x64 - Release|Win32 = Release|Win32 - Release|x64 = Release|x64 - EndGlobalSection - GlobalSection(ProjectConfigurationPlatforms) = postSolution - {26AF88DC-1933-4A1B-9991-21DF11DCE388}.Debug|Win32.ActiveCfg = Debug|Win32 - {26AF88DC-1933-4A1B-9991-21DF11DCE388}.Debug|Win32.Build.0 = Debug|Win32 - {26AF88DC-1933-4A1B-9991-21DF11DCE388}.Debug|x64.ActiveCfg = Debug|x64 - {26AF88DC-1933-4A1B-9991-21DF11DCE388}.Debug|x64.Build.0 = Debug|x64 - {26AF88DC-1933-4A1B-9991-21DF11DCE388}.Release|Win32.ActiveCfg = Release|Win32 - {26AF88DC-1933-4A1B-9991-21DF11DCE388}.Release|Win32.Build.0 = Release|Win32 - {26AF88DC-1933-4A1B-9991-21DF11DCE388}.Release|x64.ActiveCfg = Release|x64 - {26AF88DC-1933-4A1B-9991-21DF11DCE388}.Release|x64.Build.0 = Release|x64 - {DE1D9363-5455-4448-8D69-D22BE47F5A82}.Debug|Win32.ActiveCfg = Debug|Win32 - {DE1D9363-5455-4448-8D69-D22BE47F5A82}.Debug|Win32.Build.0 = Debug|Win32 - {DE1D9363-5455-4448-8D69-D22BE47F5A82}.Debug|x64.ActiveCfg = Debug|x64 - {DE1D9363-5455-4448-8D69-D22BE47F5A82}.Debug|x64.Build.0 = Debug|x64 - {DE1D9363-5455-4448-8D69-D22BE47F5A82}.Release|Win32.ActiveCfg = Release|Win32 - {DE1D9363-5455-4448-8D69-D22BE47F5A82}.Release|Win32.Build.0 = Release|Win32 - {DE1D9363-5455-4448-8D69-D22BE47F5A82}.Release|x64.ActiveCfg = Release|x64 - {DE1D9363-5455-4448-8D69-D22BE47F5A82}.Release|x64.Build.0 = Release|x64 - {898289D0-0D57-4B8E-97AE-013114F85DE9}.Debug|Win32.ActiveCfg = Debug|Win32 - {898289D0-0D57-4B8E-97AE-013114F85DE9}.Debug|Win32.Build.0 = Debug|Win32 - {898289D0-0D57-4B8E-97AE-013114F85DE9}.Debug|x64.ActiveCfg = Debug|x64 - {898289D0-0D57-4B8E-97AE-013114F85DE9}.Debug|x64.Build.0 = Debug|x64 - {898289D0-0D57-4B8E-97AE-013114F85DE9}.Release|Win32.ActiveCfg = Release|Win32 - {898289D0-0D57-4B8E-97AE-013114F85DE9}.Release|Win32.Build.0 = Release|Win32 - {898289D0-0D57-4B8E-97AE-013114F85DE9}.Release|x64.ActiveCfg = Release|x64 - {898289D0-0D57-4B8E-97AE-013114F85DE9}.Release|x64.Build.0 = Release|x64 - EndGlobalSection - GlobalSection(SolutionProperties) = preSolution - HideSolutionNode = FALSE - EndGlobalSection - GlobalSection(NestedProjects) = preSolution - {DE1D9363-5455-4448-8D69-D22BE47F5A82} = {4E3673B0-1BE6-41B7-9060-17A0B272CF19} - {898289D0-0D57-4B8E-97AE-013114F85DE9} = {4E3673B0-1BE6-41B7-9060-17A0B272CF19} - EndGlobalSection -EndGlobal diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGButton.cpp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGButton.cpp deleted file mode 100644 index 9c82046f..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGButton.cpp +++ /dev/null @@ -1,308 +0,0 @@ -// AGButton.cpp : ʵļ -// - -#include "stdafx.h" -#include "AGButton.h" - - -// CAGButton - -IMPLEMENT_DYNAMIC(CAGButton, CButton) - -CAGButton::CAGButton() -{ - m_crBorderNormal = RGB(0, 160, 239); - m_crBorderHover = RGB(0, 160, 239); - m_crBorderPush = RGB(0, 160, 239); - m_crBorderDisable = RGB(0, 160, 239); - - m_crBackNormal = RGB(0, 160, 239); - m_crBackHover = RGB(0, 160, 239); - m_crBackPush = RGB(0, 160, 239); - m_crBackDisable = RGB(0, 160, 239); - - m_crTextNormal = RGB(0xFF, 0xFF, 0xFF); - m_crTextHover = RGB(0xFF, 0xC8, 0x64); - m_crTextPush = RGB(0xFF, 0xC8, 0x64); - m_crTextDisable = RGB(0xCC, 0xCC, 0xCC); - - m_bHover = FALSE; - m_bMouseTrack = FALSE; - m_bFrameEffect = TRUE; - - m_nDefStatus = AGBTN_NORMAL; -} - -CAGButton::~CAGButton() -{ - m_imgBack.DeleteImageList(); -} - - -BEGIN_MESSAGE_MAP(CAGButton, CButton) - ON_WM_MOUSEMOVE() - ON_WM_MOUSELEAVE() - ON_WM_ERASEBKGND() -END_MESSAGE_MAP() - - - -// CAGButton Ϣ - -BOOL CAGButton::SetBackImage(UINT nIDResource, COLORREF crMask) -{ - CBitmap bmBackImage; - BITMAP bmImageInfo; - - if (!bmBackImage.LoadBitmap(nIDResource)) - return FALSE; - - bmBackImage.GetBitmap(&bmImageInfo); - - m_imgBack.DeleteImageList(); - if (!m_imgBack.Create(bmImageInfo.bmWidth / 4, bmImageInfo.bmHeight, ILC_COLOR24 | ILC_MASK, 4, 1)) - return FALSE; - - m_imgBack.Add(&bmBackImage, crMask); - bmBackImage.DeleteObject(); - - Invalidate(FALSE); - - return TRUE; -} - -void CAGButton::SetBackColor(COLORREF crNormal, COLORREF crHover, COLORREF crPush, COLORREF crDisable) -{ - m_crBackNormal = crNormal; - m_crBackHover = crHover; - m_crBackPush = crPush; - m_crBackDisable = crDisable; - - Invalidate(FALSE); -} - -void CAGButton::SetTextColor(COLORREF crNormal, COLORREF crHover, COLORREF crPush, COLORREF crDisable) -{ - m_crTextNormal = crNormal; - m_crTextHover = crHover; - m_crTextPush = crPush; - m_crTextDisable = crDisable; - - Invalidate(FALSE); -} - -void CAGButton::SetBorderColor(COLORREF crNormal, COLORREF crHover, COLORREF crPush, COLORREF crDisable) -{ - m_crBorderNormal = crNormal; - m_crBorderHover = crHover; - m_crBorderPush = crPush; - m_crBorderDisable = crDisable; - - Invalidate(FALSE); -} - -void CAGButton::EnableFrameEffect(BOOL bEnable) -{ - m_bFrameEffect = bEnable; - Invalidate(FALSE); -} - -void CAGButton::PreSubclassWindow() -{ - // TODO: ڴרô/û - ModifyStyle(0, BS_OWNERDRAW); - - CButton::PreSubclassWindow(); -} - - - -void CAGButton::DrawItem(LPDRAWITEMSTRUCT lpDrawItemStruct) -{ - ASSERT(lpDrawItemStruct->CtlType == ODT_BUTTON); - - UINT nStat = m_nDefStatus; - UINT uStyle = DFCS_BUTTONPUSH; - - if (m_bHover && m_nDefStatus == AGBTN_NORMAL) - nStat = AGBTN_HOVER; - - if (lpDrawItemStruct->itemState & ODS_SELECTED) { - uStyle |= DFCS_PUSHED; - nStat = AGBTN_PUSH; - } - else if (lpDrawItemStruct->itemState & ODS_DISABLED) - nStat = AGBTN_DISABLE; - - DrawBack(lpDrawItemStruct, nStat); - DrawText(lpDrawItemStruct, nStat); - - if (m_bFrameEffect) - DrawFrame(lpDrawItemStruct, nStat); -} - -void CAGButton::DrawBack(LPDRAWITEMSTRUCT lpDrawItemStruct, UINT nStat) -{ - int nImageIndex = -1; - COLORREF crBackColor = m_crBackNormal; - CDC *pDC = CDC::FromHandle(lpDrawItemStruct->hDC); - - switch (nStat) - { - case AGBTN_NORMAL: - nImageIndex = 0; - crBackColor = m_crBackNormal; - break; - case AGBTN_HOVER: - nImageIndex = 1; - crBackColor = m_crBackHover; - break; - case AGBTN_PUSH: - nImageIndex = 2; - crBackColor = m_crBackPush; - break; - case AGBTN_DISABLE: - nImageIndex = 3; - crBackColor = m_crBackDisable; - break; - default: - nImageIndex = 0; - crBackColor = m_crBackNormal; - break; - } - - if (m_imgBack.GetSafeHandle() == NULL || nImageIndex >= m_imgBack.GetImageCount()) - nImageIndex = -1; - - CRect rcButton; - CBrush brushBack; - - rcButton.CopyRect(&lpDrawItemStruct->rcItem); - brushBack.CreateSolidBrush(crBackColor); - pDC->FillRect(&rcButton, &brushBack); - - brushBack.DeleteObject(); - - if (nImageIndex != -1) - m_imgBack.Draw(pDC, nImageIndex, CPoint(0, 0), ILD_NORMAL); -} - -void CAGButton::DrawText(LPDRAWITEMSTRUCT lpDrawItemStruct, UINT nStat) -{ - CRect rcText; - CString strText; - - GetWindowText(strText); - rcText.CopyRect(&lpDrawItemStruct->rcItem); - - COLORREF crTextColor = m_crTextNormal; - CDC *pDC = CDC::FromHandle(lpDrawItemStruct->hDC); - - switch (nStat) - { - case AGBTN_NORMAL: - crTextColor = m_crTextNormal; - break; - case AGBTN_HOVER: - crTextColor = m_crTextHover; - break; - case AGBTN_PUSH: - crTextColor = m_crTextPush; - rcText.left += 1; - rcText.bottom += 1; - break; - case AGBTN_DISABLE: - crTextColor = m_crTextDisable; - break; - default: - crTextColor = m_crTextDisable; - break; - } - - COLORREF crOldColor = pDC->SetTextColor(crTextColor); - pDC->SetBkMode(TRANSPARENT); - pDC->DrawText(strText, &rcText, DT_SINGLELINE | DT_VCENTER | DT_CENTER); - pDC->SetTextColor(crOldColor); -} - -void CAGButton::DrawFrame(LPDRAWITEMSTRUCT lpDrawItemStruct, UINT nStat) -{ - CBrush brushBorder; - - CRect rcFocus(&lpDrawItemStruct->rcItem); - CDC *pDC = CDC::FromHandle(lpDrawItemStruct->hDC); - - rcFocus.left += 3; - rcFocus.right -= 3; - - rcFocus.top += 3; - rcFocus.bottom -= 3; - - switch (nStat) - { - case AGBTN_NORMAL: - brushBorder.CreateSolidBrush(m_crBorderNormal); - pDC->FrameRect(&lpDrawItemStruct->rcItem, &brushBorder); - break; - case AGBTN_HOVER: - brushBorder.CreateSolidBrush(m_crBorderHover); - pDC->DrawEdge(&lpDrawItemStruct->rcItem, BDR_RAISEDOUTER, BF_RECT); - break; - case AGBTN_PUSH: - brushBorder.CreateSolidBrush(m_crBorderPush); - pDC->DrawEdge(&lpDrawItemStruct->rcItem, BDR_SUNKENINNER, BF_RECT); - break; - case AGBTN_DISABLE: - brushBorder.CreateSolidBrush(m_crBorderDisable); - pDC->FrameRect(&lpDrawItemStruct->rcItem, &brushBorder); - break; - - default: - break; - } - - if (lpDrawItemStruct->itemState & ODS_FOCUS) - pDC->DrawFocusRect(&rcFocus); -} - -void CAGButton::OnMouseMove(UINT nFlags, CPoint point) -{ - // TODO: ڴϢ/Ĭֵ - if (!m_bHover){ - m_bHover = TRUE; - Invalidate(FALSE); - } - - if (!m_bMouseTrack) { - - TRACKMOUSEEVENT tmEvent; - - tmEvent.cbSize = sizeof(TRACKMOUSEEVENT); - tmEvent.dwFlags = TME_LEAVE; - tmEvent.hwndTrack = GetSafeHwnd(); - tmEvent.dwFlags = TME_LEAVE; - tmEvent.dwHoverTime = 1; - ::TrackMouseEvent(&tmEvent); - } - - CButton::OnMouseMove(nFlags, point); -} - - -void CAGButton::OnMouseLeave() -{ - // TODO: ڴϢ/Ĭֵ - m_bHover = FALSE; - m_bMouseTrack = FALSE; - Invalidate(FALSE); - - CButton::OnMouseLeave(); -} - -BOOL CAGButton::OnEraseBkgnd(CDC* pDC) -{ - // TODO: ڴϢ/Ĭֵ - - return TRUE; -// return CButton::OnEraseBkgnd(pDC); -} diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGButton.h b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGButton.h deleted file mode 100644 index 5e67d266..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGButton.h +++ /dev/null @@ -1,72 +0,0 @@ -#pragma once - - -// CAGButton - -class CAGButton : public CButton -{ - DECLARE_DYNAMIC(CAGButton) - -public: - enum { - AGBTN_NORMAL = 0, - AGBTN_HOVER, - AGBTN_PUSH, - AGBTN_DISABLE - }; - - CAGButton(); - virtual ~CAGButton(); - - BOOL SetBackImage(UINT nIDResource, COLORREF crMask = RGB(0xFF, 0x00, 0xFF)); - void SetBackColor(COLORREF crNormal, COLORREF crHover, COLORREF crPush, COLORREF crDisable); - void SetTextColor(COLORREF crNormal, COLORREF crHover, COLORREF crPush, COLORREF crDisable); - void SetBorderColor(COLORREF crNormal, COLORREF crHover, COLORREF crPush, COLORREF crDisable); - - void EnableFrameEffect(BOOL bEnable = TRUE); - void SwitchButtonStatus(UINT nStatus = AGBTN_NORMAL) { m_nDefStatus = nStatus; }; - -protected: - virtual void PreSubclassWindow(); - virtual void DrawItem(LPDRAWITEMSTRUCT lpDrawItemStruct); - - afx_msg void OnMouseMove(UINT nFlags, CPoint point); - afx_msg void OnMouseLeave(); - afx_msg BOOL OnEraseBkgnd(CDC* pDC); - - DECLARE_MESSAGE_MAP() - -protected: - void DrawBack(LPDRAWITEMSTRUCT lpDrawItemStruct, UINT nStat); - void DrawText(LPDRAWITEMSTRUCT lpDrawItemStruct, UINT nStat); - void DrawFrame(LPDRAWITEMSTRUCT lpDrawItemStruct, UINT nStat); - -private: - CImageList m_imgBack; - - COLORREF m_crBackNormal; - COLORREF m_crBackHover; - COLORREF m_crBackPush; - COLORREF m_crBackDisable; - - COLORREF m_crTextNormal; - COLORREF m_crTextHover; - COLORREF m_crTextPush; - COLORREF m_crTextDisable; - - COLORREF m_crBorderNormal; - COLORREF m_crBorderHover; - COLORREF m_crBorderPush; - COLORREF m_crBorderDisable; - -private: - BOOL m_bHover; - BOOL m_bMouseTrack; - BOOL m_bFrameEffect; - - UINT m_nDefStatus; -public: - -}; - - diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGComboBox.cpp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGComboBox.cpp deleted file mode 100644 index c660dbcd..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGComboBox.cpp +++ /dev/null @@ -1,682 +0,0 @@ -// AGComboBox.cpp : ʵļ -// - -#include "stdafx.h" -#include "AGComboBox.h" - -IMPLEMENT_DYNAMIC(CAGComboBoxList, CWnd) - -CAGComboBoxList::CAGComboBoxList() -: m_nItemCount(0) -, m_nCurSel(-1) -, m_nCurPointIndex(-1) -, m_crBack(RGB(0xF5, 0xF5, 0xF5)) -, m_crBorder(RGB(0xC8, 0xC8, 0xC8)) -, m_crText(RGB(0x00, 0x00, 0x00)) -, m_crTextHot(RGB(0x00, 0x9E, 0xEB)) -, m_lpWndFont(NULL) -{ - m_penBorder.CreatePen(PS_SOLID, 1, m_crBorder); -} - -CAGComboBoxList::~CAGComboBoxList() -{ - m_imgSel.DeleteImageList(); - m_penBorder.DeleteObject(); -} - -BEGIN_MESSAGE_MAP(CAGComboBoxList, CWnd) - ON_WM_PAINT() - ON_WM_MOUSEMOVE() -// ON_WM_MOUSELEAVE() - ON_WM_LBUTTONDOWN() - ON_WM_MOUSEWHEEL() -// ON_WM_VSCROLL() - ON_WM_CREATE() - ON_WM_SHOWWINDOW() -// ON_WM_ERASEBKGND() -END_MESSAGE_MAP() - -BOOL CAGComboBoxList::Create(DWORD dwStyle, const RECT& rect, CWnd* pParentWnd, CAGComboBox *pAGComboBox, UINT nID) -{ - ASSERT(pAGComboBox != NULL); - - m_lpComboBox = pAGComboBox; - - m_ctrVScroll.Create(SBS_VERT | SBS_LEFTALIGN | WS_CHILD | WS_VISIBLE, CRect(5, 30, 30, 130), this, nID+1); - - return CWnd::Create(NULL, NULL, dwStyle, rect, GetDesktopWindow(), nID, NULL); -} - -int CAGComboBoxList::GetCount() const -{ - return m_nItemCount; -} - -int CAGComboBoxList::GetCurSel() const -{ - return m_nCurSel; -} - -DWORD_PTR CAGComboBoxList::GetItemData(int nIndex) const -{ - return m_arrItemPtrData.GetAt(nIndex); -} - -void CAGComboBoxList::GetText(int nIndex, CString& rString) const -{ - rString.Empty(); - - if (m_nItemCount == 0) - return; - - if (nIndex >= 0 && nIndex < m_nItemCount) { - rString = m_arrItemString.GetAt(nIndex); - return; - } -} - -int CAGComboBoxList::SetItemData(int nIndex, DWORD_PTR dwItemData) -{ - ASSERT(nIndex >= 0 && nIndex <= m_nItemCount); - - m_arrItemPtrData.SetAt(nIndex, dwItemData); - - return nIndex; -} - -int CAGComboBoxList::AddString(LPCTSTR lpszString) -{ - return InsertString(m_nItemCount, lpszString); -} - -int CAGComboBoxList::InsertString(int nIndex, LPCTSTR lpszString) -{ - ASSERT(nIndex >= 0 && nIndex <= m_nItemCount); - - int nRet = -1; - DWORD_PTR dwItemData = 0; - - if (nIndex >= 0 && nIndex <= m_nItemCount) { - m_arrItemString.InsertAt(nIndex, lpszString); - m_arrItemPtrData.InsertAt(nIndex, dwItemData); - m_nItemCount++; - - if (m_nCurSel >= nIndex) - m_nCurSel += 1; - } - - return nRet; -} - -int CAGComboBoxList::SetCurSel(int nSelect) -{ - if (nSelect < -1 || nSelect >= m_nItemCount) - return -1; - - m_nCurSel = nSelect; - - return m_nCurSel; -} - -int CAGComboBoxList::DeleteString(int nIndex) -{ - if (nIndex < -1 || nIndex >= m_nItemCount) - return -1; - - m_arrItemPtrData.RemoveAt(nIndex, 1); - m_arrItemString.RemoveAt(nIndex, 1); - - if (m_nCurSel == nIndex) - m_nCurSel = -1; - else if (m_nCurSel > nIndex) - m_nCurSel -= 1; - - m_nItemCount--; - - return m_nItemCount; -} - -void CAGComboBoxList::ResetContent() -{ - m_arrItemPtrData.RemoveAll(); - m_arrItemString.RemoveAll(); - m_nItemCount = 0; - m_nCurSel = -1; -} - -void CAGComboBoxList::SetFont(CFont* pFont, BOOL bRedraw) -{ - ASSERT(pFont != NULL); - - m_lpWndFont = pFont; - Invalidate(bRedraw); -} - -void CAGComboBoxList::SetItemHeight(int nItemHeight) -{ - m_nPerItemHeight = nItemHeight; - Invalidate(TRUE); -} - -int CAGComboBoxList::GetItemHeight() const -{ - return m_nPerItemHeight; -} - -void CAGComboBoxList::ShowVScrollBar(BOOL bShow) -{ - -} - - -void CAGComboBoxList::OnPaint() -{ - CPaintDC dc(this); - - CRect rcClient; - CRect rcBack; - CRect rcText; - CRect rcSel; - SCROLLINFO si; - - memset(&si, 0, sizeof(SCROLLINFO)); - si.cbSize = sizeof(si); - si.fMask = SIF_ALL; - GetScrollInfo(SB_VERT, &si); - int nStartIndex = si.nPos / m_nPerItemHeight; - - GetClientRect(&rcClient); - rcBack.SetRect(rcClient.left + 1, rcClient.top + 1, rcClient.right - 1, rcClient.bottom - 1); - rcText.SetRect(5, 1, rcClient.Width() - 35, m_nPerItemHeight-2); - - dc.SetBkMode(TRANSPARENT); - CPen *lpOldPen = dc.SelectObject(&m_penBorder); - - dc.Rectangle(&rcClient); - dc.FillSolidRect(&rcBack, m_crBack); - dc.SelectObject(m_lpWndFont); - - for (int nIndex = 0; nIndex < m_nItemCount - nStartIndex; nIndex++) { - - dc.SetTextColor(m_crText); - const CString &strItem = m_arrItemString.GetAt(nIndex + nStartIndex); - - dc.FillSolidRect(&rcText, m_crBack); - if (m_nCurSel == (nStartIndex + nIndex)){ - ; - } - - if (m_nCurPointIndex == (nStartIndex + nIndex)) - dc.SetTextColor(m_crTextHot); - - dc.DrawText(strItem, &rcText, DT_SINGLELINE | DT_LEFT | DT_VCENTER | DT_END_ELLIPSIS); - rcText.OffsetRect(0, m_nPerItemHeight); - } - - dc.SelectObject(lpOldPen); -} - -void CAGComboBoxList::OnMouseMove(UINT nFlags, CPoint point) -{ - CRect rcClient; - CRect rcDirty; - int nCurPointIndex = 0; - - GetClientRect(&rcClient); - if (rcClient.PtInRect(point) && m_nItemCount > 0) - nCurPointIndex = point.y / m_nPerItemHeight; - else - nCurPointIndex = -1; - - if (nCurPointIndex != m_nCurPointIndex) { - rcDirty.SetRect(0, nCurPointIndex*m_nPerItemHeight, rcClient.Width(), (nCurPointIndex + 1)*m_nPerItemHeight); - m_nCurPointIndex = nCurPointIndex; - Invalidate(FALSE); - } - - CWnd::OnMouseMove(nFlags, point); -} - -void CAGComboBoxList::OnLButtonDown(UINT nFlags, CPoint point) -{ - CRect rcClient; - SCROLLINFO si; - - memset(&si, 0, sizeof(SCROLLINFO)); - si.cbSize = sizeof(si); - si.fMask = SIF_ALL; - - GetScrollInfo(SB_VERT, &si); - int nStartIndex = si.nPos / m_nPerItemHeight; - - GetClientRect(&rcClient); - if (!rcClient.PtInRect(point)) - m_nCurPointIndex = -1; - else { - if (m_nCurSel != m_nCurPointIndex + nStartIndex) { - m_nCurSel = m_nCurPointIndex + nStartIndex; - m_lpComboBox->GetParent()->SendMessage(WM_COMMAND, MAKEWPARAM(m_lpComboBox->GetDlgCtrlID(), CBN_SELCHANGE), (LPARAM)m_lpComboBox->GetSafeHwnd()); - } - - if (m_nCurSel != -1) { - if (m_nCurSel > (m_nItemCount - 1)) { - m_nCurSel = m_nItemCount - 1; - } - m_lpComboBox->SetWindowText(m_arrItemString.GetAt(m_nCurSel)); - } - } - m_lpComboBox->ShowDropDown(FALSE); - - CWnd::OnLButtonDown(nFlags, point); -} - -BOOL CAGComboBoxList::OnMouseWheel(UINT nFlags, short zDelta, CPoint pt) -{ - // TODO: ڴϢ/Ĭֵ - SCROLLINFO si; - int nVertPos = 0; - - si.cbSize = sizeof(si); - si.fMask = SIF_ALL; - GetScrollInfo(SB_VERT, &si); - nVertPos = si.nPos; - si.nPos -= 2 * zDelta; - si.fMask = SIF_POS; - SetScrollPos(SB_VERT, si.nPos, TRUE); - Invalidate(FALSE); - - return CWnd::OnMouseWheel(nFlags, zDelta, pt); -} - -int CAGComboBoxList::OnCreate(LPCREATESTRUCT lpCreateStruct) -{ - if (CWnd::OnCreate(lpCreateStruct) == -1) - return -1; - - // TODO: ڴרõĴ - ModifyStyleEx(0, WS_EX_TOOLWINDOW); - SetWindowPos(&wndTopMost, 0, 0, 0, 0, SWP_NOSIZE | SWP_NOMOVE); - - return 0; -} - - -void CAGComboBoxList::OnShowWindow(BOOL bShow, UINT nStatus) -{ - CWnd::OnShowWindow(bShow, nStatus); - - // TODO: ڴ˴Ϣ - if (bShow) - SetCapture(); - else - ReleaseCapture(); - - CWnd::OnShowWindow(bShow, nStatus); -} - -/* -BOOL CAGComboBoxList::OnEraseBkgnd(CDC* pDC) -{ - // TODO: ڴϢ/Ĭֵ - CRect rcClient; - CRect rcBack; - - GetClientRect(&rcClient); - ClientToScreen(&rcClient); - rcBack.CopyRect(&rcClient); - rcBack.left += 1; - rcBack.top += 1; - rcBack.right -= 1; - rcBack.bottom -= 1; - - CPen *lpOldPen = pDC->SelectObject(&m_penBorder); - pDC->Rectangle(&rcClient); - pDC->FillSolidRect(&rcBack, m_crBack); - - pDC->SelectObject(lpOldPen); - - return TRUE; - // return CWnd::OnEraseBkgnd(pDC); -} -*/ - -// CAGComboBox - -IMPLEMENT_DYNAMIC(CAGComboBox, CWnd) - -CAGComboBox::CAGComboBox() -: m_nMaxListHeight(200) -, m_nBtnStat(0) -, m_crBack(RGB(0xF5, 0xF5, 0xF5)) -, m_crBorder(RGB(0xC8, 0xC8, 0xC8)) -, m_crTextNormal(RGB(0x00, 0x00, 0x00)) -, m_crTextHot(RGB(0x00, 0x9E, 0xEB)) -, m_bMouseTrack(FALSE) -, m_lpWndFont(NULL) -{ - m_penBorder.CreatePen(PS_SOLID, 1, RGB(0xC8, 0xC8, 0xC8)); -} - -CAGComboBox::~CAGComboBox() -{ - m_imgDropBtn.DeleteImageList(); - - m_penBorder.DeleteObject(); -} - - -BEGIN_MESSAGE_MAP(CAGComboBox, CWnd) - ON_WM_PAINT() - ON_WM_MOUSEMOVE() - ON_WM_MOUSELEAVE() - ON_WM_LBUTTONDOWN() - ON_WM_ERASEBKGND() -END_MESSAGE_MAP() - - -BOOL CAGComboBox::Create(DWORD dwStyle, const RECT& rect, CWnd* pParentWnd, UINT nID) -{ - CRect rcListBox; - - rcListBox.left = rect.left; - rcListBox.right = rect.right; - rcListBox.top = rect.bottom + 1; - rcListBox.bottom = rcListBox.top + rect.bottom - rect.top; - - m_ctrList.Create(WS_CHILD | WS_VSCROLL, rcListBox, GetDesktopWindow(), this, nID + 1); - m_ctrList.ShowWindow(SW_HIDE); - - return CWnd::Create(NULL, _T(""), dwStyle, rect, pParentWnd, nID, NULL); -} - -int CAGComboBox::GetCount() const -{ - return m_ctrList.GetCount(); -} - -int CAGComboBox::GetCurSel() const -{ - return m_ctrList.GetCurSel(); -} - -DWORD_PTR CAGComboBox::GetItemData(int nIndex) const -{ - return m_ctrList.GetItemData(nIndex); -} - -void CAGComboBox::GetLBText(int nIndex, CString& rString) const -{ - m_ctrList.GetText(nIndex, rString); -} - -int CAGComboBox::SetItemData(int nIndex, DWORD_PTR dwItemData) -{ - return m_ctrList.SetItemData(nIndex, dwItemData); -} - -void CAGComboBox::ShowDropDown(BOOL bShowIt) -{ - CRect rcClient; - int nItemHeight = m_ctrList.GetItemHeight(); - - GetClientRect(&rcClient); - if (nItemHeight == 0) { - nItemHeight = rcClient.Height(); - m_ctrList.SetItemHeight(nItemHeight); - } - rcClient.OffsetRect(0, rcClient.Height() + 1); - - int nMaxCanvasHeight = m_ctrList.GetCount()*nItemHeight; - m_ctrList.ShowVScrollBar(FALSE); - if (nMaxCanvasHeight == 0) - rcClient.bottom = rcClient.top + m_ctrList.GetItemHeight(); - else if (nMaxCanvasHeight > 0 && nMaxCanvasHeight < m_nMaxListHeight) - rcClient.bottom = rcClient.top + nMaxCanvasHeight; - else{ - rcClient.bottom = rcClient.top + m_nMaxListHeight; - if (nMaxCanvasHeight > m_nMaxListHeight) - m_ctrList.ShowVScrollBar(TRUE); - } - - if (bShowIt) - m_ctrList.ShowWindow(SW_SHOW); - else { - m_ctrList.ShowWindow(SW_HIDE); - Invalidate(TRUE); - } - - ClientToScreen(&rcClient); - m_ctrList.MoveWindow(&rcClient, FALSE); -} - -void CAGComboBox::SetListMaxHeight(int nMaxHeight) -{ - m_nMaxListHeight = nMaxHeight; -} - -int CAGComboBox::AddString(LPCTSTR lpszString) -{ - return m_ctrList.AddString(lpszString); -} - -int CAGComboBox::InsertString(int nIndex, LPCTSTR lpszString) -{ - return m_ctrList.InsertString(nIndex, lpszString); -} - -int CAGComboBox::SetCurSel(int nSelect) -{ - CString str; - int nCurSel = m_ctrList.SetCurSel(nSelect); - - GetLBText(nCurSel, str); - Invalidate(TRUE); - - return nCurSel; -} - -int CAGComboBox::DeleteString(int nIndex) -{ - int nCurSel = m_ctrList.GetCurSel(); - int nCurCount = m_ctrList.DeleteString(nIndex); - - if (nCurSel == nIndex) - Invalidate(TRUE); - - return nCurCount; -} - -void CAGComboBox::ResetContent() -{ - m_ctrList.ResetContent(); - Invalidate(TRUE); -} - -BOOL CAGComboBox::GetDroppedState() const -{ - return m_ctrList.IsWindowVisible(); -} - -int CAGComboBox::GetListMaxHeight() const -{ - return m_nMaxListHeight; -} - -BOOL CAGComboBox::SetButtonImage(UINT nIDButton, int cx, int cy, COLORREF crMask) -{ - CBitmap bmpButton; - - if (!bmpButton.LoadBitmap(nIDButton)) - return FALSE; - - m_imgDropBtn.DeleteImageList(); - m_imgDropBtn.Create(cx, cy, ILC_COLOR24 | ILC_MASK, 4, 1); - m_imgDropBtn.Add(&bmpButton, crMask); - - bmpButton.DeleteObject(); - - Invalidate(FALSE); - - return TRUE; -} - -void CAGComboBox::SetFaceColor(COLORREF crBorder, COLORREF crBack) -{ - m_crBorder = crBorder; - m_crBack = crBack; - - Invalidate(); -} - -void CAGComboBox::SetTextColor(COLORREF crNormal, COLORREF crHot) -{ - m_crTextNormal = crNormal; - m_crTextHot = crHot; -} - -void CAGComboBox::SetFont(CFont* pFont, BOOL bRedraw) -{ - ASSERT(pFont != NULL); - - m_lpWndFont = pFont; - m_ctrList.SetFont(m_lpWndFont, bRedraw); - - Invalidate(bRedraw); -} - -// CAGComboBox Ϣ - -void CAGComboBox::OnPaint() -{ - CPaintDC dc(this); // device context for painting - // TODO: ڴ˴Ϣ - // ΪͼϢ CWnd::OnPaint() - CString str; - CRect rcClient; - CRect rcText; - CPoint ptButton; - IMAGEINFO imgInfo; - CFont *lpOldFont = NULL; - - GetClientRect(&rcClient); - rcText.CopyRect(&rcClient); - rcText.left += 10; - rcText.right -= (rcClient.Height() + 15); - - dc.SetBkMode(TRANSPARENT); - COLORREF crOldColor = dc.SetBkColor(m_crBack); - - if (m_imgDropBtn.GetSafeHandle() != NULL) { - m_imgDropBtn.GetImageInfo(0, &imgInfo); - - int nImageHeight = imgInfo.rcImage.bottom - imgInfo.rcImage.top; - ptButton.x = rcClient.Width() - imgInfo.rcImage.right - 1; - ptButton.y = (rcClient.Height() - nImageHeight) / 2; - m_imgDropBtn.Draw(&dc, m_nBtnStat, ptButton, ILD_NORMAL); - } - - if (m_lpWndFont != NULL) - lpOldFont = dc.SelectObject(m_lpWndFont); - - if (m_nBtnStat == AGCBXBTN_NORMAL || m_nBtnStat == AGCBXBTN_DISABLE) - dc.SetTextColor(m_crTextNormal); - else - dc.SetTextColor(m_crTextHot); - - GetLBText(m_ctrList.GetCurSel(), str); - dc.DrawText(str, &rcText, DT_SINGLELINE | DT_LEFT | DT_VCENTER | DT_END_ELLIPSIS); - - if (lpOldFont != NULL) - dc.SelectObject(lpOldFont); -} - -void CAGComboBox::OnMouseMove(UINT nFlags, CPoint point) -{ - CRect rcClient; - UINT nBtnStat = AGCBXBTN_NORMAL; - - if (!GetDroppedState()) - nBtnStat = AGCBXBTN_HOVER; - - if (m_nBtnStat != nBtnStat) - Invalidate(FALSE); - - m_nBtnStat = nBtnStat; - - if (!m_bMouseTrack) { - - TRACKMOUSEEVENT tmEvent; - - tmEvent.cbSize = sizeof(TRACKMOUSEEVENT); - tmEvent.dwFlags = TME_LEAVE; - tmEvent.hwndTrack = GetSafeHwnd(); - tmEvent.dwFlags = TME_LEAVE; - tmEvent.dwHoverTime = 1; - ::TrackMouseEvent(&tmEvent); - } - - CWnd::OnMouseMove(nFlags, point); -} - -void CAGComboBox::OnMouseLeave() -{ - UINT nBtnStat = AGCBXBTN_NORMAL; - - m_bMouseTrack = FALSE; - if (!GetDroppedState()) - nBtnStat = AGCBXBTN_NORMAL; - - if (m_nBtnStat != nBtnStat) - Invalidate(FALSE); - - m_nBtnStat = nBtnStat; - - CWnd::OnMouseLeave(); -} - -void CAGComboBox::OnLButtonDown(UINT nFlags, CPoint point) -{ - SetFocus(); - - BOOL bDropped = GetDroppedState(); - - if (bDropped) { - m_nBtnStat = AGCBXBTN_NORMAL; - } - else { - m_nBtnStat = AGCBXBTN_PUSH; - } - - ShowDropDown(!bDropped); - - CWnd::OnLButtonDown(nFlags, point); -} - -BOOL CAGComboBox::OnEraseBkgnd(CDC* pDC) -{ - // TODO: ڴϢ/Ĭֵ - CRect rcClient; - CRect rcBack; - - GetClientRect(&rcClient); - rcBack.CopyRect(&rcClient); - rcBack.left += 1; - rcBack.right -= 1; - rcBack.top += 1; - rcBack.bottom -= 1; - - pDC->SetBkMode(TRANSPARENT); - COLORREF crOldColor = pDC->SetBkColor(m_crBack); - - CPen *lpOldPen = pDC->SelectObject(&m_penBorder); - - if ( (GetStyle()&WS_BORDER) != 0) - pDC->Rectangle(&rcClient); - - pDC->FillSolidRect(&rcBack, m_crBack); - - return TRUE; -} - - diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGComboBox.h b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGComboBox.h deleted file mode 100644 index dd2e6874..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGComboBox.h +++ /dev/null @@ -1,158 +0,0 @@ -#pragma once - -#include - -#define WM_AGCBXNOTIFY_SELCHANGE WM_USER+ - -class CAGComboBox; -// CAGComboBox -class CAGComboBoxList : public CWnd -{ - DECLARE_DYNAMIC(CAGComboBoxList) - -public: - CAGComboBoxList(); - virtual ~CAGComboBoxList(); - - virtual BOOL Create(DWORD dwStyle, const RECT& rect, CWnd* pParentWnd, CAGComboBox *pAGComboBox, UINT nID); - - int GetCount() const; - int GetCurSel() const; - DWORD_PTR GetItemData(int nIndex) const; - void GetText(int nIndex, CString& rString) const; - - int SetItemData(int nIndex, DWORD_PTR dwItemData); - int AddString(LPCTSTR lpszString); - int InsertString(int nIndex, LPCTSTR lpszString); - - int SetCurSel(int nSelect); - int DeleteString(int nIndex); - void ResetContent(); - - void SetFont(CFont* pFont, BOOL bRedraw = TRUE); - void SetItemHeight(int nItemHeight); - int GetItemHeight() const; - - void ShowVScrollBar(BOOL bShow); -protected: - afx_msg void OnPaint(); - afx_msg void OnMouseMove(UINT nFlags, CPoint point); - afx_msg void OnLButtonDown(UINT nFlags, CPoint point); - afx_msg BOOL OnMouseWheel(UINT nFlags, short zDelta, CPoint pt); -// afx_msg void OnVScroll(UINT nSBCode, UINT nPos, CScrollBar* pScrollBar); - afx_msg int OnCreate(LPCREATESTRUCT lpCreateStruct); - afx_msg void OnShowWindow(BOOL bShow, UINT nStatus); -// afx_msg BOOL OnEraseBkgnd(CDC* pDC); - - DECLARE_MESSAGE_MAP() - -protected: - - // the resource to draw the control -private: - CImageList m_imgSel; - CPen m_penBorder; - CFont *m_lpWndFont; - - COLORREF m_crBack; - COLORREF m_crBorder; - COLORREF m_crText; - COLORREF m_crTextHot; - - // the controls -private: - CAGComboBox *m_lpComboBox; - CScrollBar m_ctrVScroll; - - // private data -private: - CStringArray m_arrItemString; - CArray m_arrItemPtrData; - - int m_nItemCount; - int m_nCurSel; - int m_nCurPointIndex; - int m_nPerItemHeight; - -public: - - - -}; - -class CAGComboBox : public CWnd -{ - enum { - AGCBXBTN_NORMAL = 0, - AGCBXBTN_HOVER, - AGCBXBTN_PUSH, - AGCBXBTN_DISABLE, - }; - - DECLARE_DYNAMIC(CAGComboBox) - -public: - CAGComboBox(); - virtual ~CAGComboBox(); - - virtual BOOL Create(DWORD dwStyle, const RECT& rect, CWnd* pParentWnd, UINT nID); - - int GetCount() const; - int GetCurSel() const; - DWORD_PTR GetItemData(int nIndex) const; - void GetLBText(int nIndex, CString& rString) const; - - int SetItemData(int nIndex, DWORD_PTR dwItemData); - void ShowDropDown(BOOL bShowIt); - void SetListMaxHeight(int nMaxHeight); - - int AddString(LPCTSTR lpszString); - int InsertString(int nIndex, LPCTSTR lpszString); - - int SetCurSel(int nSelect); - int DeleteString(int nIndex); - void ResetContent(); - - BOOL GetDroppedState() const; - int GetListMaxHeight() const; - - BOOL SetButtonImage(UINT nIDButton, int cx, int cy, COLORREF crMask); - void SetFaceColor(COLORREF crBorder, COLORREF crBack); - void SetTextColor(COLORREF crNormal, COLORREF crHot); - void SetFont(CFont* pFont, BOOL bRedraw = TRUE); - -protected: - afx_msg void OnPaint(); - afx_msg void OnMouseMove(UINT nFlags, CPoint point); - afx_msg void OnMouseLeave(); - afx_msg void OnLButtonDown(UINT nFlags, CPoint point); - afx_msg BOOL OnEraseBkgnd(CDC* pDC); - - DECLARE_MESSAGE_MAP() - -protected: - void OnDrawTextCtrl(CDC *pDC); - void OnDrawBtnCtrl(CDC *pDC); - -private: - CImageList m_imgDropBtn; - CPen m_penBorder; - - COLORREF m_crBack; - COLORREF m_crBorder; - - COLORREF m_crTextNormal; - COLORREF m_crTextHot; - - UINT m_nBtnStat; - int m_nMaxListHeight; - BOOL m_bMouseTrack; - - CFont *m_lpWndFont; - -private: - CAGComboBoxList m_ctrList; - -}; - - diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGConfig.cpp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGConfig.cpp deleted file mode 100644 index 51e6588a..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGConfig.cpp +++ /dev/null @@ -1,155 +0,0 @@ -#include "stdafx.h" -#include "AGConfig.h" - - -CAGConfig::CAGConfig() -{ - ::GetModuleFileName(NULL, m_szConfigFile, MAX_PATH); - LPTSTR lpLastSlash = _tcsrchr(m_szConfigFile, _T('\\')) + 1; - _tcscpy_s(lpLastSlash, MAX_PATH, _T("VideoConfig.ini")); - - if (::GetFileAttributes(m_szConfigFile) == INVALID_FILE_ATTRIBUTES){ - HANDLE hFile = ::CreateFile(m_szConfigFile, GENERIC_WRITE, FILE_SHARE_READ, NULL, OPEN_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL); - ::CloseHandle(hFile); - } -} - - -CAGConfig::~CAGConfig() -{ -} - -int CAGConfig::GetCodec() -{ -#ifdef ENABLE_CODEC - CString strCodec; - - ::GetPrivateProfileString(_T("VideoConfig"), _T("CodecIndex"), _T("1"), strCodec.GetBuffer(MAX_PATH), MAX_PATH, m_szConfigFile); - - strCodec.ReleaseBuffer(); - - return _ttoi(strCodec); -#else - return 0; -#endif -} - -BOOL CAGConfig::SetCodec(int nCodec) -{ -#ifdef ENABLE_CODEC - CString strCodec; - - strCodec.Format(_T("%d"), nCodec); - - return ::WritePrivateProfileString(_T("VideoConfig"), _T("CodecIndex"), strCodec, m_szConfigFile); -#else - return TRUE; -#endif -} - -/* -int CAGConfig::GetResolution() -{ - CString strResolution; - - ::GetPrivateProfileString(_T("VideoConfig"), _T("ResolutionIndex"), _T("1"), strResolution.GetBuffer(MAX_PATH), MAX_PATH, m_szConfigFile); - - strResolution.ReleaseBuffer(); - - return _ttoi(strResolution); -} - -BOOL CAGConfig::SetResolution(int nResolution) -{ - CString strResolution; - - strResolution.Format(_T("%d"), nResolution); - - return ::WritePrivateProfileString(_T("VideoConfig"), _T("ResolutionIndex"), strResolution, m_szConfigFile); -} - -int CAGConfig::GetFPS() -{ - CString strFps; - - ::GetPrivateProfileString(_T("VideoConfig"), _T("FPSIndex"), _T("1"), strFps.GetBuffer(MAX_PATH), MAX_PATH, m_szConfigFile); - - strFps.ReleaseBuffer(); - - return _ttoi(strFps); -} - -BOOL CAGConfig::SetFPS(int nPFS) -{ - CString strFPS; - - strFPS.Format(_T("%d"), nPFS); - - return ::WritePrivateProfileString(_T("VideoConfig"), _T("FPSIndex"), strFPS, m_szConfigFile); - -} - -int CAGConfig::GetMaxRate() -{ - CString strMaxRate; - - ::GetPrivateProfileString(_T("VideoConfig"), _T("MaxRatePos"), _T("1"), strMaxRate.GetBuffer(MAX_PATH), MAX_PATH, m_szConfigFile); - - strMaxRate.ReleaseBuffer(); - - return _ttoi(strMaxRate); -} - -BOOL CAGConfig::SetMaxRate(int nMaxRate) -{ - CString strMaxRate; - - strMaxRate.Format(_T("%d"), nMaxRate); - - return ::WritePrivateProfileString(_T("VideoConfig"), _T("MaxRatePos"), strMaxRate, m_szConfigFile); -} -*/ - - -int CAGConfig::GetSolution() -{ - CString strResolution; - - ::GetPrivateProfileString(_T("VideoConfig"), _T("SolutionIndex"), _T("1"), strResolution.GetBuffer(MAX_PATH), MAX_PATH, m_szConfigFile); - - strResolution.ReleaseBuffer(); - - return _ttoi(strResolution); -} - -BOOL CAGConfig::SetSolution(int nResolution) -{ - CString strResolution; - - strResolution.Format(_T("%d"), nResolution); - - return ::WritePrivateProfileString(_T("VideoConfig"), _T("SolutionIndex"), strResolution, m_szConfigFile); -} - -BOOL CAGConfig::EnableAutoSave(BOOL bEnable) -{ - CString strSave; - - if (bEnable) - strSave = _T("1"); - else - strSave = _T("0"); - - return ::WritePrivateProfileString(_T("VideoConfig"), _T("SaveSetting"), strSave, m_szConfigFile); -} - -BOOL CAGConfig::IsAutoSaveEnabled() -{ - CString strSaveSetting; - - ::GetPrivateProfileString(_T("VideoConfig"), _T("SaveSetting"), _T("0"), strSaveSetting.GetBuffer(MAX_PATH), MAX_PATH, m_szConfigFile); - - strSaveSetting.ReleaseBuffer(); - - return (_ttoi(strSaveSetting) == 1) ? TRUE : FALSE; -} \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGConfig.h b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGConfig.h deleted file mode 100644 index 2ccb0d9d..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGConfig.h +++ /dev/null @@ -1,29 +0,0 @@ -#pragma once -class CAGConfig -{ -public: - CAGConfig(); - ~CAGConfig(); - - int GetCodec(); - BOOL SetCodec(int nCodec); - -/* int GetResolution(); - BOOL SetResolution(int nResolution); - - int GetFPS(); - BOOL SetFPS(int nPFS); - - int GetMaxRate(); - BOOL SetMaxRate(int nMaxRate); -*/ - BOOL EnableAutoSave(BOOL bEnable); - BOOL IsAutoSaveEnabled(); - - BOOL SetSolution(int nIndex); - int GetSolution(); - -private: - TCHAR m_szConfigFile[MAX_PATH]; -}; - diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGDesktopCaptureDlg.cpp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGDesktopCaptureDlg.cpp deleted file mode 100644 index f9d0e387..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGDesktopCaptureDlg.cpp +++ /dev/null @@ -1,229 +0,0 @@ -// AGDesktopCaptureDlg.cpp : ʵļ -// - -#include "stdafx.h" -#include "OpenVideoCall.h" -#include "AGDesktopCaptureDlg.h" -#include "afxdialogex.h" - - -// CAGDesktopCaptureDlg Ի - -IMPLEMENT_DYNAMIC(CAGDesktopCaptureDlg, CDialogEx) - -CAGDesktopCaptureDlg::CAGDesktopCaptureDlg(CWnd* pParent /*=NULL*/) - : CDialogEx(CAGDesktopCaptureDlg::IDD, pParent) - , m_bMouseLDown(FALSE) -{ - -} - -CAGDesktopCaptureDlg::~CAGDesktopCaptureDlg() -{ -} - -void CAGDesktopCaptureDlg::DoDataExchange(CDataExchange* pDX) -{ - CDialogEx::DoDataExchange(pDX); -} - - -BEGIN_MESSAGE_MAP(CAGDesktopCaptureDlg, CDialogEx) - ON_WM_MOUSEMOVE() - ON_WM_LBUTTONDOWN() - ON_WM_LBUTTONUP() - ON_WM_PAINT() - ON_WM_ERASEBKGND() - ON_WM_LBUTTONDBLCLK() - ON_WM_RBUTTONDOWN() -END_MESSAGE_MAP() - - -// CAGDesktopCaptureDlg Ϣ -BOOL CAGDesktopCaptureDlg::SaveScreen(LPCRECT lpRect) -{ - CDC dcDesktop; - CRect rcDesktop; - CRect rcDest; - - CBitmap *lpOldBitmap = NULL; - - CWnd *lpWndDesktop = GetDesktopWindow(); - CDC *lpDCDesktop = lpWndDesktop->GetDC(); - - lpWndDesktop->GetWindowRect(&rcDesktop); - - if (lpRect == NULL) - rcDest.CopyRect(&rcDesktop); - else { - if (lpRect->left < rcDesktop.left || lpRect->top < rcDesktop.top || lpRect->right > rcDesktop.right || lpRect->bottom > rcDesktop.bottom) - return FALSE; - else - rcDest.CopyRect(lpRect); - } - - dcDesktop.CreateCompatibleDC(lpDCDesktop); - - if (m_bmpDesktop.GetSafeHandle() != NULL) - m_bmpDesktop.DeleteObject(); - - m_bmpDesktop.CreateCompatibleBitmap(lpDCDesktop, rcDest.Width(), rcDest.Height()); - lpOldBitmap = dcDesktop.SelectObject(&m_bmpDesktop); - dcDesktop.BitBlt(0, 0, rcDesktop.Width(), rcDesktop.Height(), lpDCDesktop, 0, 0, SRCCOPY); - dcDesktop.SelectObject(lpOldBitmap); - - return TRUE; -} - -void CAGDesktopCaptureDlg::OnPaint() -{ - CPaintDC dc(this); - CDC dcBuffer; - CBitmap bmpBuffer; - // TODO: ڴ˴Ϣ - // ΪͼϢ CWnd::OnPaint() - CRect rcWindow; - BLENDFUNCTION blend; - GetWindowRect(&rcWindow); - - CBrush brBack; - brBack.CreateSolidBrush(RGB(0x00, 0x00, 0x00)); - dcBuffer.CreateCompatibleDC(&dc); - bmpBuffer.CreateCompatibleBitmap(&dc, rcWindow.Width(), rcWindow.Height()); - - CBitmap *lpOldBitmap = dcBuffer.SelectObject(&bmpBuffer); - dcBuffer.FillRect(&rcWindow, &brBack); - - blend.BlendOp = AC_SRC_OVER; - blend.AlphaFormat = 0; - blend.SourceConstantAlpha = 0x80; - blend.BlendFlags = 0; - - dc.AlphaBlend(0, 0, rcWindow.Width(), rcWindow.Height(), &dcBuffer, 0, 0, rcWindow.Width(), rcWindow.Height(), blend); - - if (m_bMouseLDown) { - CDC dcBitmap; - CPen penMark; - CString strTip; - - penMark.CreatePen(PS_SOLID, 4, RGB(0x00, 0xA0, 0xE9)); - - dcBitmap.CreateCompatibleDC(&dc); - dcBitmap.SelectObject(&m_bmpDesktop); - dc.BitBlt(m_rcRegion.left, m_rcRegion.top, m_rcRegion.Width(), m_rcRegion.Height(), &dcBitmap, m_rcRegion.left, m_rcRegion.top, SRCCOPY); - - dc.SelectObject(&penMark); - dc.SelectStockObject(NULL_BRUSH); - dc.Rectangle(&m_rcRegion); - - strTip = _T("double click to share the desktop region or ESC to abort"); - // dc.SetBkMode(TRANSPARENT); - dc.SetBkColor(RGB(0x00, 0xA0, 0xE9)); - dc.SetTextColor(RGB(0xFF, 0xFF, 0xFF)); - dc.TextOut(m_rcRegion.left + 10, m_rcRegion.top + 10, strTip); - } -} - -void CAGDesktopCaptureDlg::OnLButtonDblClk(UINT nFlags, CPoint point) -{ - // TODO: ڴϢ/Ĭֵ - CRect rcRegion; - DESKTOP_SHARE_PARAM deskShareParam; - int nFPS = m_dlgCapSet.GetCaptureFPS(); - m_dlgCapSet.ShowWindow(SW_HIDE); - m_dlgCapSet.GetCaptureRect(&rcRegion); - - deskShareParam.nX = rcRegion.left; - deskShareParam.nY = rcRegion.top; - deskShareParam.nWidth = rcRegion.Width(); - deskShareParam.nHeight = rcRegion.Height(); - deskShareParam.nFPS = m_dlgCapSet.GetCaptureFPS(); - deskShareParam.nBitrate = m_dlgCapSet.GetBitrate(); - - GetParent()->SendMessage(WM_DESKTOPSHARE, (WPARAM)&deskShareParam, NULL); - // CDialogEx::OnLButtonDblClk(nFlags, point); - CDialogEx::OnOK(); -} - -void CAGDesktopCaptureDlg::OnRButtonDown(UINT nFlags, CPoint point) -{ - // TODO: ڴϢ/Ĭֵ - - // CDialogEx::OnRButtonDown(nFlags, point); - m_dlgCapSet.ShowWindow(SW_HIDE); - CDialogEx::OnOK(); -} - -void CAGDesktopCaptureDlg::OnLButtonDown(UINT nFlags, CPoint point) -{ - // TODO: ڴϢ/Ĭֵ - m_bMouseLDown = TRUE; - m_ptStart = point; - - - CDialogEx::OnLButtonDown(nFlags, point); -} - - -void CAGDesktopCaptureDlg::OnLButtonUp(UINT nFlags, CPoint point) -{ - // TODO: ڴϢ/Ĭֵ - m_bMouseLDown = FALSE; - m_ptEnd = point; - - //m_dlgCapSet.MoveWindow(m_rcRegion.left + 10, m_rcRegion.top + 40, 440, 80); - m_dlgCapSet.ShowWindow(SW_SHOW); - - if (m_rcRegion.right == m_rcRegion.left - || m_rcRegion.bottom == m_rcRegion.top){ - return; - } - m_dlgCapSet.SetCaptureRect(&m_rcRegion); - - CDialogEx::OnLButtonUp(nFlags, point); -} - -void CAGDesktopCaptureDlg::OnMouseMove(UINT nFlags, CPoint point) -{ - // TODO: ڴϢ/Ĭֵ - CRect rcMarkWnd; - - if (m_bMouseLDown) { - m_ptEnd = point; - - m_rcRegion.left = m_ptStart.x < m_ptEnd.x ? m_ptStart.x : m_ptEnd.x; - m_rcRegion.top = m_ptStart.y < m_ptEnd.y ? m_ptStart.y : m_ptEnd.y; - - m_rcRegion.right = m_ptStart.x >= m_ptEnd.x ? m_ptStart.x : m_ptEnd.x; - m_rcRegion.bottom = m_ptStart.y >= m_ptEnd.y ? m_ptStart.y : m_ptEnd.y; - - InvalidateRect(&m_rcRegion, FALSE); - } - - CDialogEx::OnMouseMove(nFlags, point); -} -BOOL CAGDesktopCaptureDlg::OnEraseBkgnd(CDC* pDC) -{ - // TODO: ڴϢ/Ĭֵ - CDC dcBuffer; - dcBuffer.CreateCompatibleDC(pDC); - dcBuffer.SelectObject(&m_bmpDesktop); - - CRect rcWindow; - GetWindowRect(&rcWindow); - pDC->BitBlt(0, 0, rcWindow.Width(), rcWindow.Height(), &dcBuffer, 0, 0, SRCCOPY); - - return TRUE; -} - - -BOOL CAGDesktopCaptureDlg::OnInitDialog() -{ - CDialogEx::OnInitDialog(); - - // TODO: ڴӶijʼ - m_dlgCapSet.Create(CDskcapsetDlg::IDD, this); - - return TRUE; // return TRUE unless you set the focus to a control - // 쳣: OCX ҳӦ FALSE -} diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGDesktopCaptureDlg.h b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGDesktopCaptureDlg.h deleted file mode 100644 index 1812006e..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGDesktopCaptureDlg.h +++ /dev/null @@ -1,57 +0,0 @@ -#pragma once -#include "DskcapsetDlg.h" - -// CAGDesktopCaptureDlg Ի - -#define WM_DESKTOPSHARE WM_USER+304 - -typedef struct _DESKTOP_SHARE_PARAM -{ - int nX; - int nY; - int nWidth; - int nHeight; - int nFPS; - int nBitrate; - -} DESKTOP_SHARE_PARAM, *PDESKTOP_SHARE_PARAM, *LPDESKTOP_SHARE_PARAM; - -class CAGDesktopCaptureDlg : public CDialogEx -{ - DECLARE_DYNAMIC(CAGDesktopCaptureDlg) - -public: - CAGDesktopCaptureDlg(CWnd* pParent = NULL); // ׼캯 - virtual ~CAGDesktopCaptureDlg(); - - BOOL SaveScreen(LPCRECT lpRect); -// Ի - enum { IDD = IDD_SCRCAP_DIALOG }; - -protected: - virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV ֧ - virtual BOOL OnInitDialog(); - - afx_msg void OnMouseMove(UINT nFlags, CPoint point); - afx_msg void OnPaint(); - - afx_msg BOOL OnEraseBkgnd(CDC* pDC); - - afx_msg void OnLButtonDblClk(UINT nFlags, CPoint point); - afx_msg void OnRButtonDown(UINT nFlags, CPoint point); - afx_msg void OnLButtonDown(UINT nFlags, CPoint point); - afx_msg void OnLButtonUp(UINT nFlags, CPoint point); - - DECLARE_MESSAGE_MAP() - -private: - CBitmap m_bmpDesktop; - BOOL m_bMouseLDown; - - CPoint m_ptStart; - CPoint m_ptEnd; - CRect m_rcRegion; - -// CComboBox m_cmbFrameRate; - CDskcapsetDlg m_dlgCapSet; -}; diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGEdit.cpp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGEdit.cpp deleted file mode 100644 index a776660f..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGEdit.cpp +++ /dev/null @@ -1,196 +0,0 @@ -// AGEdit.cpp : ʵļ -// - -#include "stdafx.h" -#include "AGEdit.h" - - -// CAGEdit - -IMPLEMENT_DYNAMIC(CAGEdit, CEdit) - -CAGEdit::CAGEdit() -: m_crBorder(RGB(0xD8, 0xD8, 0xD8)) -, m_crBack(RGB(0xFF, 0xFF, 0xFF)) -, m_crText(RGB(0x00, 0xA0, 0xE9)) -, m_crTip(RGB(0xD8, 0xD8, 0xD8)) -, m_strTip(_T("ı")) -, m_bTrackMouseEvent(FALSE) -, m_bOverControl(FALSE) -, m_bEmpty(TRUE) -, m_bTexting(FALSE) -{ - m_penBorder.CreatePen(PS_SOLID, 1, m_crBorder); - m_brushBack.CreateSolidBrush(m_crBack); -} - -CAGEdit::~CAGEdit() -{ - m_penBorder.DeleteObject(); - m_brushBack.DeleteObject(); -} - - -BEGIN_MESSAGE_MAP(CAGEdit, CEdit) - ON_WM_ERASEBKGND() - ON_WM_CTLCOLOR_REFLECT() - ON_WM_MOUSEHOVER() - ON_WM_MOUSEMOVE() - ON_WM_MOUSELEAVE() - ON_WM_SETFOCUS() - ON_WM_KILLFOCUS() - ON_WM_CHAR() - ON_CONTROL_REFLECT(EN_CHANGE, &CAGEdit::OnEnChange) - ON_WM_CREATE() -END_MESSAGE_MAP() - - - -// CAGEdit Ϣ -void CAGEdit::SetTip(LPCTSTR lpTip) -{ - m_strTip = lpTip; - - Invalidate(TRUE); -} - -void CAGEdit::SetColor(COLORREF crBorder, COLORREF crBack, COLORREF crText, COLORREF crTip) -{ - if (crBorder != m_crBorder){ - m_penBorder.DeleteObject(); - m_crBorder = crBorder; - m_penBorder.CreatePen(PS_SOLID, 1, m_crBorder); - } - - if (crBack != m_crBack){ - m_brushBack.DeleteObject(); - m_crBack = crBack; - m_brushBack.CreateSolidBrush(m_crBack); - } - - Invalidate(); -} - -BOOL CAGEdit::OnEraseBkgnd(CDC* pDC) -{ - // TODO: ڴϢ/Ĭֵ - CRect rcWindow; - - GetWindowRect(&rcWindow); - - CPen *lpDefaultPen = pDC->SelectObject(&m_penBorder); - pDC->Rectangle(&rcWindow); - pDC->SelectObject(lpDefaultPen); - - return CEdit::OnEraseBkgnd(pDC); -} - -HBRUSH CAGEdit::CtlColor(CDC* pDC, UINT nCtlColor) -{ - // TODO: ڴ˸ DC κ - pDC->SetBkColor(m_crBack); - - if (m_bEmpty) - pDC->SetTextColor(m_crTip); - else - pDC->SetTextColor(m_crText); - - // TODO: ӦøĴ򷵻ط null - return (HBRUSH)m_brushBack; //༭ɫˢ -} - -void CAGEdit::OnMouseHover(UINT nFlags, CPoint point) -{ - // TODO: ڴϢ/Ĭֵ - - CEdit::OnMouseHover(nFlags, point); -} - - -void CAGEdit::OnMouseMove(UINT nFlags, CPoint point) -{ - // TODO: ڴϢ/Ĭֵ - if (!m_bTrackMouseEvent) { - TRACKMOUSEEVENT TrackMouseEvent; - TrackMouseEvent.cbSize = sizeof(TRACKMOUSEEVENT); - TrackMouseEvent.hwndTrack = GetSafeHwnd(); - TrackMouseEvent.dwFlags = TME_LEAVE | TME_HOVER; - TrackMouseEvent.dwHoverTime = HOVER_DEFAULT; - - m_bTrackMouseEvent = ::TrackMouseEvent(&TrackMouseEvent); - } - - CEdit::OnMouseMove(nFlags, point); -} - - -void CAGEdit::OnMouseLeave() -{ - // TODO: ڴϢ/Ĭֵ - m_bTrackMouseEvent = FALSE; - - CEdit::OnMouseLeave(); -} - - -void CAGEdit::OnSetFocus(CWnd* pOldWnd) -{ - CEdit::OnSetFocus(pOldWnd); - - // TODO: ڴ˴Ϣ - if (m_bEmpty) { - m_bTexting = FALSE; - SetWindowText(_T("")); - } - -} - - -void CAGEdit::OnKillFocus(CWnd* pNewWnd) -{ - CEdit::OnKillFocus(pNewWnd); - - // TODO: ڴ˴Ϣ - m_bTexting = FALSE; - if (m_bEmpty) - SetWindowText(m_strTip); -} - - -void CAGEdit::OnChar(UINT nChar, UINT nRepCnt, UINT nFlags) -{ - // TODO: ڴϢ/Ĭֵ - m_bTexting = TRUE; - - if (GetWindowTextLength() <= 2) - Invalidate(); - - CEdit::OnChar(nChar, nRepCnt, nFlags); -} - - -void CAGEdit::OnEnChange() -{ - // TODO: ÿؼ RICHEDIT ؼ - // ʹ֪ͨд CEdit::OnInitDialog() - // CRichEditCtrl().SetEventMask() - // ͬʱ ENM_CHANGE ־㵽С - - // TODO: ڴӿؼ֪ͨ - if (m_bTexting) - m_bEmpty = (GetWindowTextLength() == 0) ? TRUE : FALSE; -} - - -int CAGEdit::OnCreate(LPCREATESTRUCT lpCreateStruct) -{ - if (CEdit::OnCreate(lpCreateStruct) == -1) - return -1; - - // TODO: ڴרõĴ - m_bTexting = FALSE; - if (m_bEmpty) - SetWindowText(m_strTip); - - return 0; -} diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGEdit.h b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGEdit.h deleted file mode 100644 index 692e7e8a..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGEdit.h +++ /dev/null @@ -1,52 +0,0 @@ -#pragma once - - -// CAGEdit - -class CAGEdit : public CEdit -{ - DECLARE_DYNAMIC(CAGEdit) - -public: - CAGEdit(); - virtual ~CAGEdit(); - - void SetTip(LPCTSTR lpTip); - CString GetTip() { return m_strTip; }; - void SetColor(COLORREF crBorder, COLORREF crBack, COLORREF crText, COLORREF crTip = RGB(0xD8, 0xD8, 0xD8)); - -protected: - afx_msg int OnCreate(LPCREATESTRUCT lpCreateStruct); - afx_msg BOOL OnEraseBkgnd(CDC* pDC); - afx_msg HBRUSH CtlColor(CDC* pDC, UINT nCtlColor); - afx_msg void OnMouseHover(UINT nFlags, CPoint point); - afx_msg void OnMouseMove(UINT nFlags, CPoint point); - afx_msg void OnMouseLeave(); - - afx_msg void OnSetFocus(CWnd* pOldWnd); - afx_msg void OnKillFocus(CWnd* pNewWnd); - - afx_msg void OnChar(UINT nChar, UINT nRepCnt, UINT nFlags); - afx_msg void OnEnChange(); - - DECLARE_MESSAGE_MAP() - -private: - CString m_strTip; - - COLORREF m_crBorder; - COLORREF m_crBack; - COLORREF m_crText; - COLORREF m_crTip; - - CPen m_penBorder; - CBrush m_brushBack; - - BOOL m_bTrackMouseEvent; - BOOL m_bOverControl; - - BOOL m_bEmpty; - BOOL m_bTexting; -}; - - diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGEngineEventHandler.cpp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGEngineEventHandler.cpp deleted file mode 100644 index 0e20334d..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGEngineEventHandler.cpp +++ /dev/null @@ -1,379 +0,0 @@ -#include "StdAfx.h" -#include "AGEngineEventHandler.h" -#include "AGEventDef.h" - -CAGEngineEventHandler::CAGEngineEventHandler(void) -{ -} - -CAGEngineEventHandler::~CAGEngineEventHandler(void) -{ -} - -void CAGEngineEventHandler::SetMsgReceiver(HWND hWnd) -{ - m_hMainWnd = hWnd; -} - -void CAGEngineEventHandler::onJoinChannelSuccess(const char* channel, uid_t uid, int elapsed) -{ - LPAGE_JOINCHANNEL_SUCCESS lpData = new AGE_JOINCHANNEL_SUCCESS; - - int nChannelLen = strlen(channel) + 1; - lpData->channel = new char[nChannelLen]; - lpData->uid = uid; - lpData->elapsed = elapsed; - - strcpy_s(lpData->channel, nChannelLen, channel); - - if(m_hMainWnd != NULL) - ::PostMessage(m_hMainWnd, WM_MSGID(EID_JOINCHANNEL_SUCCESS), (WPARAM)lpData, 0); -} - -void CAGEngineEventHandler::onRejoinChannelSuccess(const char* channel, uid_t uid, int elapsed) -{ - LPAGE_REJOINCHANNEL_SUCCESS lpData = new AGE_REJOINCHANNEL_SUCCESS; - - int nChannelLen = strlen(channel) + 1; - lpData->channel = new char[nChannelLen]; - lpData->uid = uid; - lpData->elapsed = elapsed; - - strcpy_s(lpData->channel, nChannelLen, channel); - - if(m_hMainWnd != NULL) - ::PostMessage(m_hMainWnd, WM_MSGID(EID_REJOINCHANNEL_SUCCESS), (WPARAM)lpData, 0); - -} - -void CAGEngineEventHandler::onWarning(int warn, const char* msg) -{ - CString str; - - str = _T("onWarning"); -} - -void CAGEngineEventHandler::onError(int err, const char* msg) -{ - LPAGE_ERROR lpData = new AGE_ERROR; - - int nMsgLen = 0; - - // attention: the pointer of msg maybe NULL!!! - if(msg != NULL) { - nMsgLen = strlen(msg) + 1; - lpData->msg = new char[nMsgLen]; - strcpy_s(lpData->msg, nMsgLen, msg); - } - else - lpData->msg = NULL; - - lpData->err = err; - - - - if(m_hMainWnd != NULL) - ::PostMessage(m_hMainWnd, WM_MSGID(EID_ERROR), (WPARAM)lpData, 0); - -} - -void CAGEngineEventHandler::onAudioQuality(uid_t uid, int quality, unsigned short delay, unsigned short lost) -{ - LPAGE_AUDIO_QUALITY lpData = new AGE_AUDIO_QUALITY; - - lpData->uid = uid; - lpData->quality = quality; - lpData->delay = delay; - lpData->lost = lost; - - if(m_hMainWnd != NULL) - ::PostMessage(m_hMainWnd, WM_MSGID(EID_AUDIO_QUALITY), (WPARAM)lpData, 0); -} - - -void CAGEngineEventHandler::onAudioVolumeIndication(const AudioVolumeInfo* speakers, unsigned int speakerNumber, int totalVolume) -{ - LPAGE_AUDIO_VOLUME_INDICATION lpData = new AGE_AUDIO_VOLUME_INDICATION; - - lpData->speakers = new AudioVolumeInfo[speakerNumber]; - memcpy(lpData->speakers, speakers, speakerNumber*sizeof(AudioVolumeInfo)); - lpData->speakerNumber = speakerNumber; - lpData->totalVolume = totalVolume; - - if (m_hMainWnd != NULL) - ::PostMessage(m_hMainWnd, WM_MSGID(EID_AUDIO_VOLUME_INDICATION), (WPARAM)lpData, 0); - -} - -void CAGEngineEventHandler::onLeaveChannel(const RtcStats& stat) -{ - LPAGE_LEAVE_CHANNEL lpData = new AGE_LEAVE_CHANNEL; - - memcpy(&lpData->rtcStat, &stat, sizeof(RtcStats)); - - if(m_hMainWnd != NULL) - ::PostMessage(m_hMainWnd, WM_MSGID(EID_LEAVE_CHANNEL), (WPARAM)lpData, 0); -} - -void CAGEngineEventHandler::onRtcStats(const RtcStats& stat) -{ - CString str; - - str = _T("stat"); -} - - -void CAGEngineEventHandler::onMediaEngineEvent(int evt) -{ - LPAGE_MEDIA_ENGINE_EVENT lpData = new AGE_MEDIA_ENGINE_EVENT; - - lpData->evt = evt; - - if (m_hMainWnd != NULL) - ::PostMessage(m_hMainWnd, WM_MSGID(EID_MEDIA_ENGINE_EVENT), (WPARAM)lpData, 0); - -} - -void CAGEngineEventHandler::onAudioDeviceStateChanged(const char* deviceId, int deviceType, int deviceState) -{ - LPAGE_AUDIO_DEVICE_STATE_CHANGED lpData = new AGE_AUDIO_DEVICE_STATE_CHANGED; - - int nDeviceIDLen = strlen(deviceId) + 1; - - lpData->deviceId = new char[nDeviceIDLen]; - - strcpy_s(lpData->deviceId, nDeviceIDLen, deviceId); - lpData->deviceType = deviceType; - lpData->deviceState = deviceState; - - if (m_hMainWnd != NULL) - ::PostMessage(m_hMainWnd, WM_MSGID(EID_AUDIO_DEVICE_STATE_CHANGED), (WPARAM)lpData, 0); - -} - -void CAGEngineEventHandler::onVideoDeviceStateChanged(const char* deviceId, int deviceType, int deviceState) -{ - LPAGE_VIDEO_DEVICE_STATE_CHANGED lpData = new AGE_VIDEO_DEVICE_STATE_CHANGED; - - int nDeviceIDLen = strlen(deviceId) + 1; - - lpData->deviceId = new char[nDeviceIDLen]; - - strcpy_s(lpData->deviceId, nDeviceIDLen, deviceId); - lpData->deviceType = deviceType; - lpData->deviceState = deviceState; - - if (m_hMainWnd != NULL) - ::PostMessage(m_hMainWnd, WM_MSGID(EID_VIDEO_DEVICE_STATE_CHANGED), (WPARAM)lpData, 0); - -} - -void CAGEngineEventHandler::onLastmileQuality(int quality) -{ - LPAGE_LASTMILE_QUALITY lpData = new AGE_LASTMILE_QUALITY; - - lpData->quality = quality; - - if(m_hMainWnd != NULL) - ::PostMessage(m_hMainWnd, WM_MSGID(EID_LASTMILE_QUALITY), (WPARAM)lpData, 0); - -} - -void CAGEngineEventHandler::onFirstLocalVideoFrame(int width, int height, int elapsed) -{ - LPAGE_FIRST_LOCAL_VIDEO_FRAME lpData = new AGE_FIRST_LOCAL_VIDEO_FRAME; - - lpData->width = width; - lpData->height = height; - lpData->elapsed = elapsed; - - if(m_hMainWnd != NULL) - ::PostMessage(m_hMainWnd, WM_MSGID(EID_FIRST_LOCAL_VIDEO_FRAME), (WPARAM)lpData, 0); - -} - -void CAGEngineEventHandler::onFirstRemoteVideoDecoded(uid_t uid, int width, int height, int elapsed) -{ - LPAGE_FIRST_REMOTE_VIDEO_DECODED lpData = new AGE_FIRST_REMOTE_VIDEO_DECODED; - - lpData->uid = uid; - lpData->width = width; - lpData->height = height; - lpData->elapsed = elapsed; - - if(m_hMainWnd != NULL) - ::PostMessage(m_hMainWnd, WM_MSGID(EID_FIRST_REMOTE_VIDEO_DECODED), (WPARAM)lpData, 0); - -} - -void CAGEngineEventHandler::onFirstRemoteVideoFrame(uid_t uid, int width, int height, int elapsed) -{ - LPAGE_FIRST_REMOTE_VIDEO_FRAME lpData = new AGE_FIRST_REMOTE_VIDEO_FRAME; - - lpData->uid = uid; - lpData->width = width; - lpData->height = height; - lpData->elapsed = elapsed; - - if(m_hMainWnd != NULL) - ::PostMessage(m_hMainWnd, WM_MSGID(EID_FIRST_REMOTE_VIDEO_FRAME), (WPARAM)lpData, 0); - -} - -void CAGEngineEventHandler::onUserJoined(uid_t uid, int elapsed) -{ - LPAGE_USER_JOINED lpData = new AGE_USER_JOINED; - - lpData->uid = uid; - lpData->elapsed = elapsed; - - if(m_hMainWnd != NULL) - ::PostMessage(m_hMainWnd, WM_MSGID(EID_USER_JOINED), (WPARAM)lpData, 0); -} - -void CAGEngineEventHandler::onUserOffline(uid_t uid, USER_OFFLINE_REASON_TYPE reason) -{ - LPAGE_USER_OFFLINE lpData = new AGE_USER_OFFLINE; - - lpData->uid = uid; - lpData->reason = reason; - - if(m_hMainWnd != NULL) - ::PostMessage(m_hMainWnd, WM_MSGID(EID_USER_OFFLINE), (WPARAM)lpData, 0); -} - -void CAGEngineEventHandler::onUserMuteAudio(uid_t uid, bool muted) -{ - LPAGE_USER_MUTE_AUDIO lpData = new AGE_USER_MUTE_AUDIO; - - lpData->uid = uid; - lpData->muted = muted; - - if(m_hMainWnd != NULL) - ::PostMessage(m_hMainWnd, WM_MSGID(EID_USER_MUTE_AUDIO), (WPARAM)lpData, 0); - -} - -void CAGEngineEventHandler::onUserMuteVideo(uid_t uid, bool muted) -{ - LPAGE_USER_MUTE_VIDEO lpData = new AGE_USER_MUTE_VIDEO; - - lpData->uid = uid; - lpData->muted = muted; - - if(m_hMainWnd != NULL) - ::PostMessage(m_hMainWnd, WM_MSGID(EID_USER_MUTE_VIDEO), (WPARAM)lpData, 0); - -} - -void CAGEngineEventHandler::onStreamMessage(uid_t uid, int streamId, const char* data, size_t length) -{ - LPAGE_STREAM_MESSAGE lpData = new AGE_STREAM_MESSAGE; - - lpData->uid = uid; - lpData->streamId = streamId; - lpData->data = new char[length]; - lpData->length = length; - - memcpy_s(lpData->data, length, data, length); - - if (m_hMainWnd != NULL) - ::PostMessage(m_hMainWnd, WM_MSGID(EID_STREAM_MESSAGE), (WPARAM)lpData, 0); - -} - -void CAGEngineEventHandler::onApiCallExecuted(const char* api, int error) -{ - LPAGE_APICALL_EXECUTED lpData = new AGE_APICALL_EXECUTED; - - strcpy_s(lpData->api, 128, api); - lpData->error = error; - - if (m_hMainWnd != NULL) - ::PostMessage(m_hMainWnd, WM_MSGID(EID_APICALL_EXECUTED), (WPARAM)lpData, 0); -} - -void CAGEngineEventHandler::onLocalVideoStats(const LocalVideoStats& stats) -{ - LPAGE_LOCAL_VIDEO_STAT lpData = new AGE_LOCAL_VIDEO_STAT; - - lpData->sentBitrate = stats.sentBitrate; - lpData->sentFrameRate = stats.sentFrameRate; - - if(m_hMainWnd != NULL) - ::PostMessage(m_hMainWnd, WM_MSGID(EID_LOCAL_VIDEO_STAT), (WPARAM)lpData, 0); - -} - -void CAGEngineEventHandler::onRemoteVideoStats(const RemoteVideoStats& stats) -{ - LPAGE_REMOTE_VIDEO_STAT lpData = new AGE_REMOTE_VIDEO_STAT; - - lpData->uid = stats.uid; - lpData->delay = stats.delay; - lpData->width = stats.width; - lpData->height = stats.height; - lpData->rendererOutputFrameRate = stats.rendererOutputFrameRate; - lpData->receivedBitrate = stats.receivedBitrate; - lpData->decoderOutputFrameRate = stats.decoderOutputFrameRate; - - if(m_hMainWnd != NULL) - ::PostMessage(m_hMainWnd, WM_MSGID(EID_REMOTE_VIDEO_STAT), (WPARAM)lpData, 0); -} - -void CAGEngineEventHandler::onCameraReady() -{ - if(m_hMainWnd != NULL) - ::PostMessage(m_hMainWnd, WM_MSGID(EID_CAMERA_READY), 0, 0); - -} - -void CAGEngineEventHandler::onVideoStopped() -{ - if (m_hMainWnd != NULL) - ::PostMessage(m_hMainWnd, WM_MSGID(EID_VIDEO_STOPPED), 0, 0); -} - -void CAGEngineEventHandler::onConnectionLost() -{ - if(m_hMainWnd != NULL) - ::PostMessage(m_hMainWnd, WM_MSGID(EID_CONNECTION_LOST), 0, 0); -} - -void CAGEngineEventHandler::onConnectionInterrupted() -{ - CString str; - - str = _T("onConnectionInterrupted"); -} - -void CAGEngineEventHandler::onUserEnableVideo(uid_t uid, bool enabled) -{ -// if (m_hMainWnd != NULL) -// ::PostMessage(m_hMainWnd, WM_MSGID(EID_CONNECTION_LOST), 0, 0); - -} - -void CAGEngineEventHandler::onStartRecordingService(int error) -{ - if (m_hMainWnd != NULL) - ::PostMessage(m_hMainWnd, WM_MSGID(EID_START_RCDSRV), 0, 0); - -} - -void CAGEngineEventHandler::onStopRecordingService(int error) -{ - if (m_hMainWnd != NULL) - ::PostMessage(m_hMainWnd, WM_MSGID(EID_STOP_RCDSRV), 0, 0); - -} - -void CAGEngineEventHandler::onRefreshRecordingServiceStatus(int status) -{ - LPAGE_RCDSRV_STATUS lpData = new AGE_RCDSRV_STATUS; - - lpData->status = status; - - if (m_hMainWnd != NULL) - ::PostMessage(m_hMainWnd, WM_MSGID(EID_REFREASH_RCDSRV), (WPARAM)lpData, 0); -} \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGEngineEventHandler.h b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGEngineEventHandler.h deleted file mode 100644 index 821599b5..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGEngineEventHandler.h +++ /dev/null @@ -1,55 +0,0 @@ -#pragma once - -using namespace agora::rtc; - -class CAGEngineEventHandler : - public IRtcEngineEventHandler -{ -public: - CAGEngineEventHandler(void); - ~CAGEngineEventHandler(void); - - void SetMsgReceiver(HWND hWnd = NULL); - HWND GetMsgReceiver() {return m_hMainWnd;}; - - virtual void onJoinChannelSuccess(const char* channel, uid_t uid, int elapsed); - virtual void onRejoinChannelSuccess(const char* channel, uid_t uid, int elapsed); - virtual void onWarning(int warn, const char* msg); - virtual void onError(int err, const char* msg); - virtual void onAudioQuality(uid_t uid, int quality, unsigned short delay, unsigned short lost); - virtual void onAudioVolumeIndication(const AudioVolumeInfo* speakers, unsigned int speakerNumber, int totalVolume); - - virtual void onLeaveChannel(const RtcStats& stat); - virtual void onRtcStats(const RtcStats& stat); - virtual void onMediaEngineEvent(int evt); - - virtual void onAudioDeviceStateChanged(const char* deviceId, int deviceType, int deviceState); - virtual void onVideoDeviceStateChanged(const char* deviceId, int deviceType, int deviceState); - - virtual void onLastmileQuality(int quality); - virtual void onFirstLocalVideoFrame(int width, int height, int elapsed); - virtual void onFirstRemoteVideoDecoded(uid_t uid, int width, int height, int elapsed); - virtual void onFirstRemoteVideoFrame(uid_t uid, int width, int height, int elapsed); - virtual void onUserJoined(uid_t uid, int elapsed); - virtual void onUserOffline(uid_t uid, USER_OFFLINE_REASON_TYPE reason); - virtual void onUserMuteAudio(uid_t uid, bool muted); - virtual void onUserMuteVideo(uid_t uid, bool muted); - virtual void onApiCallExecuted(const char* api, int error); - - virtual void onStreamMessage(uid_t uid, int streamId, const char* data, size_t length); - - virtual void onLocalVideoStats(const LocalVideoStats& stats); - virtual void onRemoteVideoStats(const RemoteVideoStats& stats); - virtual void onCameraReady(); - virtual void onVideoStopped(); - virtual void onConnectionLost(); - virtual void onConnectionInterrupted(); - - virtual void onUserEnableVideo(uid_t uid, bool enabled); - - virtual void onStartRecordingService(int error); - virtual void onStopRecordingService(int error); - virtual void onRefreshRecordingServiceStatus(int status); -private: - HWND m_hMainWnd; -}; diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGEventDef.h b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGEventDef.h deleted file mode 100644 index 5b88bae5..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGEventDef.h +++ /dev/null @@ -1,255 +0,0 @@ -#ifndef _AG_EVENT_DEFINE_H_ -#define _AG_EVENT_DEFINE_H_ - -#define WM_MSGID(code) (WM_USER+0x200+code) -#define WM_EVTID(code) (code-0x200-WM_USER) - -typedef struct _AGE_JOINCHANNEL_SUCCESS -{ - char *channel; - uid_t uid; - int elapsed; - -} AGE_JOINCHANNEL_SUCCESS, *PAGE_JOINCHANNEL_SUCCESS, *LPAGE_JOINCHANNEL_SUCCESS; - -#define EID_JOINCHANNEL_SUCCESS 0x00000001 - -typedef AGE_JOINCHANNEL_SUCCESS AGE_REJOINCHANNEL_SUCCESS, *PAGE_REJOINCHANNEL_SUCCESS, *LPAGE_REJOINCHANNEL_SUCCESS ; - -#define EID_REJOINCHANNEL_SUCCESS 0x00000002 - -typedef struct _AGE_ERROR -{ - int err; - char *msg; - -} AGE_ERROR, *PAGE_ERROR, *LPAGE_ERROR; - -#define EID_ERROR 0x00000003 - -typedef struct _AGE_AUDIO_QUALITY { - uid_t uid; - int quality; - unsigned short delay; - unsigned short lost; - -} AGE_AUDIO_QUALITY, *PAGE_AUDIO_QUALITY, *LPAGE_AUDIO_QUALITY; - -#define EID_AUDIO_QUALITY 0x00000004 - -typedef struct _AGE_AUDIO_TRANSPORT_QUALITY -{ - uid_t uid; - unsigned short delay; - unsigned short lost; - -} AGE_AUDIO_TRANSPORT_QUALITY, *PAGE_AUDIO_TRANSPORT_QUALITY, *LPAGE_AUDIO_TRANSPORT_QUALITY; - -#define EID_AUDIO_TRANSPORT_QUALITY 0x00000005 - -typedef AGE_AUDIO_TRANSPORT_QUALITY AGE_VIDEO_TRANSPORT_QUALITY, *PAGE_VIDEO_TRANSPORT_QUALITY, *LPAGE_VIDEO_TRANSPORT_QUALITY; - -#define EID_VUDIO_TRANSPORT_QUALITY 0x00000006 - -typedef struct _AGE_RECAP -{ - char* recapData; - int length; - -} AGE_RECAP, *PAGE_RECAP, *LPAGE_RECAP; - -#define EID_RECAP 0x00000007 - -typedef struct _AGE_AUDIO_VOLUME_INDICATION -{ - AudioVolumeInfo *speakers; - unsigned int speakerNumber; - int totalVolume; - -} AGE_AUDIO_VOLUME_INDICATION, *PAGE_AUDIO_VOLUME_INDICATION, *LPAGE_AUDIO_VOLUME_INDICATION; - -#define EID_AUDIO_VOLUME_INDICATION 0x00000008 - -typedef struct _AGE_LEAVE_CHANNEL -{ - RtcStats rtcStat; - -} AGE_LEAVE_CHANNEL, *PAGE_LEAVE_CHANNEL, *LPAGE_LEAVE_CHANNEL; - -#define EID_LEAVE_CHANNEL 0x00000009 - -typedef AGE_LEAVE_CHANNEL AGE_UPDATE_SESSION_STATS, *PAGE_UPDATE_SESSION_STATS, *LPAGE_UPDATE_SESSION_STATS; - -#define EID_UPDATE_SESSION_STATS 0x0000000A - -typedef struct _AGE_MEDIA_ENGINE_EVENT -{ - int evt; - -} AGE_MEDIA_ENGINE_EVENT, *PAGE_MEDIA_ENGINE_EVENT, *LPAGE_MEDIA_ENGINE_EVENT; - -#define EID_MEDIA_ENGINE_EVENT 0x0000000B - -typedef struct _AGE_AUDIO_DEVICE_STATE_CHANGED -{ - char *deviceId; - int deviceType; - int deviceState; - -} AGE_AUDIO_DEVICE_STATE_CHANGED, *PAGE_AUDIO_DEVICE_STATE_CHANGED, *LPAGE_AUDIO_DEVICE_STATE_CHANGED; - -#define EID_AUDIO_DEVICE_STATE_CHANGED 0x0000000C - - -typedef struct _AGE_LASTMILE_QUALITY -{ - int quality; - -} AGE_LASTMILE_QUALITY, *PAGE_LASTMILE_QUALITY, *LPAGE_LASTMILE_QUALITY; - -#define EID_LASTMILE_QUALITY 0x0000000D - -typedef struct _AGE_FIRST_LOCAL_VIDEO_FRAME -{ - int width; - int height; - int elapsed; - -} AGE_FIRST_LOCAL_VIDEO_FRAME, *PAGE_FIRST_LOCAL_VIDEO_FRAME, *LPAGE_FIRST_LOCAL_VIDEO_FRAME; - -#define EID_FIRST_LOCAL_VIDEO_FRAME 0x0000000E - -typedef struct _AGE_FIRST_REMOTE_VIDEO_DECODED -{ - uid_t uid; - int width; - int height; - int elapsed; - -} AGE_FIRST_REMOTE_VIDEO_DECODED, *PAGE_FIRST_REMOTE_VIDEO_DECODED, *LPAGE_FIRST_REMOTE_VIDEO_DECODED; - -#define EID_FIRST_REMOTE_VIDEO_DECODED 0x0000000F - -typedef AGE_FIRST_REMOTE_VIDEO_DECODED AGE_FIRST_REMOTE_VIDEO_FRAME, *PAGE_FIRST_REMOTE_VIDEO_FRAME, *LPAGE_FIRST_REMOTE_VIDEO_FRAME; - -#define EID_FIRST_REMOTE_VIDEO_FRAME 0x00000010 - -typedef struct _AGE_USER_JOINED -{ - uid_t uid; - int elapsed; - -} AGE_USER_JOINED, *PAGE_USER_JOINED, *LPAGE_USER_JOINED; - -#define EID_USER_JOINED 0x00000011 - -typedef struct _AGE_USER_OFFLINE -{ - uid_t uid; - USER_OFFLINE_REASON_TYPE reason; - -} AGE_USER_OFFLINE, *PAGE_USER_OFFLINE, *LPAGE_USER_OFFLINE; - -#define EID_USER_OFFLINE 0x00000012 - -typedef struct _AGE_USER_MUTE_AUDIO -{ - uid_t uid; - bool muted; - -} AGE_USER_MUTE_AUDIO, *PAGE_USER_MUTE_AUDIO, *LPAGE_USER_MUTE_AUDIO; - -#define EID_USER_MUTE_AUDIO 0x00000013 - -typedef AGE_USER_MUTE_AUDIO AGE_USER_MUTE_VIDEO, *PAGE_USER_MUTE_VIDEO, *LPAGE_USER_MUTE_VIDEO; - -#define EID_USER_MUTE_VIDEO 0x00000014 - -typedef struct _AGE_AUDIO_RECORDER_EXCEPTION -{ - int elapsed; - -} AGE_AUDIO_RECORDER_EXCEPTION, *PAGE_AUDIO_RECORDER_EXCEPTION, *LPAGE_AUDIO_RECORDER_EXCEPTION; - -#define EID_AUDIO_RECORDER_EXCEPTION 0x00000015 - -typedef struct _AGE_LOCAL_VIDEO_STAT -{ - int sentBitrate; - int sentFrameRate; - -} AGE_LOCAL_VIDEO_STAT, *PAGE_LOCAL_VIDEO_STAT, *LPAGE_LOCAL_VIDEO_STAT; - -#define EID_LOCAL_VIDEO_STAT 0x00000016 - -typedef struct _AGE_REMOTE_VIDEO_STAT -{ - uid_t uid; - int delay; - int width; - int height; - int receivedBitrate; - int decoderOutputFrameRate; - int rendererOutputFrameRate; - -} AGE_REMOTE_VIDEO_STAT, *PAGE_REMOTE_VIDEO_STAT, *LPAGE_REMOTE_VIDEO_STAT; - -#define EID_REMOTE_VIDEO_STAT 0x00000017 - -#define EID_CAMERA_READY 0x00000018 -#define EID_CONNECTION_LOST 0x00000019 - -#define EID_VENDOR_MESSAGE 0x0000001A -typedef struct _AGE_VENDOR_MESSAGE -{ - uid_t uid; - char* data; - size_t length; - -} AGE_VENDOR_MESSAGE, *PAGE_VENDOR_MESSAGE, *LPAGE_VENDOR_MESSAGE; - - -typedef struct _AGE_VIDEO_DEVICE_STATE_CHANGED -{ - char *deviceId; - int deviceType; - int deviceState; - -} AGE_VIDEO_DEVICE_STATE_CHANGED, *PAGE_VIDEO_DEVICE_STATE_CHANGED, *LPAGE_VIDEO_DEVICE_STATE_CHANGED; - -#define EID_VIDEO_DEVICE_STATE_CHANGED 0x0000001B - -#define EID_VIDEO_STOPPED 0x0000001C - -#define EID_START_RCDSRV 0x0000001D -#define EID_STOP_RCDSRV 0x0000001E - -typedef struct _AGE_RCDSRV_STATUS -{ - int status; - -}AGE_RCDSRV_STATUS, *PAGE_RCDSRV_STATUS, *LPAGE_RCDSRV_STATUS; - -#define EID_REFREASH_RCDSRV 0x0000001F - -typedef struct _AGE_APICALL_EXECUTED -{ - char api[128]; - int error; - -}AGE_APICALL_EXECUTED, *PAGE_APICALL_EXECUTED, *LPAGE_APICALL_EXECUTED; - -#define EID_APICALL_EXECUTED 0x00000020 - -typedef struct _AGE_STREAM_MESSAGE -{ - uid_t uid; - int streamId; - char *data; - size_t length; - -} AGE_STREAM_MESSAGE, *PAGE_STREAM_MESSAGE, *LPAGE_STREAM_MESSAGE; - -#define EID_STREAM_MESSAGE 0x00000021 - -#endif \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGHyperLink.cpp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGHyperLink.cpp deleted file mode 100644 index 9d3a6e32..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGHyperLink.cpp +++ /dev/null @@ -1,177 +0,0 @@ -// AGHyperLink.cpp : ʵļ -// - -#include "stdafx.h" -#include "AGHyperLink.h" - - -// CAGHyperLink - -IMPLEMENT_DYNAMIC(CAGHyperLink, CStatic) - -CAGHyperLink::CAGHyperLink() -{ - m_crLink = RGB(0x00, 0x9E, 0xEB); - m_crVisited = RGB(85, 26, 139); - m_crHover = RGB(255, 0, 0); - m_crBack = RGB(255, 255, 255); - m_bVisited = FALSE; // Hasn't been visited yet. - m_bOverControl = FALSE; - m_bTrackMouseEvent = FALSE; - m_strURL.Empty(); -} - -CAGHyperLink::~CAGHyperLink() -{ -} - - -BEGIN_MESSAGE_MAP(CAGHyperLink, CStatic) - ON_WM_MOUSEMOVE() - ON_WM_SETCURSOR() - ON_CONTROL_REFLECT(STN_CLICKED, &CAGHyperLink::OnStnClicked) - ON_WM_PAINT() - ON_WM_MOUSELEAVE() -END_MESSAGE_MAP() - -// CAGHyperLink Ϣ -void CAGHyperLink::PreSubclassWindow() -{ - // We want to get mouse clicks via STN_CLICKED - DWORD dwStyle = GetStyle(); - ModifyStyle(0, SS_NOTIFY, 0); - - // Set the URL as the window text - if (m_strURL.IsEmpty()) - GetWindowText(m_strURL); - - // Check that the window text isn't empty. If it is, set it as the URL. - CString strWndText; - GetWindowText(strWndText); - if (strWndText.IsEmpty()) - { - ASSERT(!m_strURL.IsEmpty()); // Window and URL both NULL. DUH! - SetWindowText(m_strURL); - } - - CStatic::PreSubclassWindow(); -} - -void CAGHyperLink::OnMouseMove(UINT nFlags, CPoint point) -{ - // TODO: ڴϢ/Ĭֵ - if (!m_bOverControl){ - m_bOverControl = TRUE; - Invalidate(FALSE); - } - - if (!m_bTrackMouseEvent) { - TRACKMOUSEEVENT TrackMouseEvent; - TrackMouseEvent.cbSize = sizeof(TRACKMOUSEEVENT); - TrackMouseEvent.hwndTrack = GetSafeHwnd(); - TrackMouseEvent.dwFlags = TME_LEAVE; - TrackMouseEvent.dwHoverTime = 1; - - m_bTrackMouseEvent = ::TrackMouseEvent(&TrackMouseEvent); - } - - CStatic::OnMouseMove(nFlags, point); -} - -BOOL CAGHyperLink::OnSetCursor(CWnd* pWnd, UINT nHitTest, UINT message) -{ - // TODO: ڴϢ/Ĭֵ - HCURSOR hLinkCursor = ::LoadCursor(NULL, IDC_HAND); - if (hLinkCursor != NULL) { - ::SetCursor(hLinkCursor); - return TRUE; - } - - return CStatic::OnSetCursor(pWnd, nHitTest, message); -} - - -void CAGHyperLink::OnStnClicked() -{ - // TODO: ڴӿؼ֪ͨ - m_bOverControl = FALSE; - - HINSTANCE hInstance = ::ShellExecute(GetParent()->GetSafeHwnd(), _T("open"), m_strURL, NULL, NULL, SW_MAXIMIZE); - if (hInstance > 0) - m_bVisited = TRUE; -} - -void CAGHyperLink::SetURL(CString strURL) -{ - m_strURL = strURL; -} - -CString CAGHyperLink::GetURL() const -{ - return m_strURL; -} - -void CAGHyperLink::SetTextColor(COLORREF crLink, COLORREF crVisited, COLORREF crHover) -{ - m_crLink = crLink; - m_crVisited = crVisited; - m_crHover = crHover; - - if(GetSafeHwnd() != NULL) - Invalidate(); -} - -void CAGHyperLink::SetBackColor(COLORREF crBack) -{ - m_crBack = crBack; -} - -COLORREF CAGHyperLink::GetLinkColor() const -{ - return m_crLink; -} - -COLORREF CAGHyperLink::GetVisitedColor() const -{ - return m_crVisited; -} - -COLORREF CAGHyperLink::GetHoverColor() const -{ - return m_crHover; -} - - -void CAGHyperLink::OnPaint() -{ - CPaintDC dc(this); // device context for painting - // TODO: ڴ˴Ϣ - // ΪͼϢ CStatic::OnPaint() - - CString strWindowText; - CRect rcClient; - - GetClientRect(&rcClient); - - CFont *lpDefaultFont = dc.SelectObject(GetFont()); - dc.SetTextColor(m_crLink); - dc.SetBkColor(m_crBack); - if (m_bOverControl) - dc.SetTextColor(m_crHover); - else if (m_bVisited) - dc.SetTextColor(m_crVisited); - - GetWindowText(strWindowText); - dc.DrawText(strWindowText, &rcClient, DT_LEFT); - dc.SelectObject(lpDefaultFont); -} - -void CAGHyperLink::OnMouseLeave() -{ - // TODO: ڴϢ/Ĭֵ - m_bTrackMouseEvent = FALSE; - m_bOverControl = FALSE; - Invalidate(FALSE); - - CStatic::OnMouseLeave(); -} diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGHyperLink.h b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGHyperLink.h deleted file mode 100644 index 8b8777a2..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGHyperLink.h +++ /dev/null @@ -1,45 +0,0 @@ -#pragma once - - -// CAGHyperLink - -class CAGHyperLink : public CStatic -{ - DECLARE_DYNAMIC(CAGHyperLink) - -public: - CAGHyperLink(); - virtual ~CAGHyperLink(); - - void SetURL(CString strURL); - CString GetURL() const; - - void SetTextColor(COLORREF crLink, COLORREF crVisited, COLORREF crHover); - void SetBackColor(COLORREF crBack); - COLORREF GetLinkColor() const; - COLORREF GetVisitedColor() const; - COLORREF GetHoverColor() const; - -protected: - virtual void PreSubclassWindow(); - - afx_msg void OnPaint(); - afx_msg void OnMouseMove(UINT nFlags, CPoint point); - afx_msg BOOL OnSetCursor(CWnd* pWnd, UINT nHitTest, UINT message); - afx_msg void OnStnClicked(); - afx_msg void OnMouseLeave(); - - DECLARE_MESSAGE_MAP() - -private: - COLORREF m_crLink; - COLORREF m_crVisited; // Hyperlink colours - COLORREF m_crHover; // Hover colour - COLORREF m_crBack; - BOOL m_bOverControl; - BOOL m_bVisited; // Has it been visited? - BOOL m_bTrackMouseEvent; - CString m_strURL; // hyperlink URL -}; - - diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGLinkCtrl.cpp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGLinkCtrl.cpp deleted file mode 100644 index b62c215d..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGLinkCtrl.cpp +++ /dev/null @@ -1,137 +0,0 @@ -// AGLinkCtrl.cpp : ʵļ -// - -#include "stdafx.h" -#include "OpenVideoCall.h" -#include "AGLinkCtrl.h" - - -// CAGLinkCtrl - -IMPLEMENT_DYNAMIC(CAGLinkCtrl, CStatic) - -CAGLinkCtrl::CAGLinkCtrl() -: m_crText(RGB(0x00, 0x9E, 0xEB)) -, m_crHover(RGB(0x00, 0xA0, 0xE9)) -, m_crBack(RGB(0xFF, 0xFF, 0xFF)) -, m_bOverControl(FALSE) -, m_bTrackMouseEvent(FALSE) -{ - -} - -CAGLinkCtrl::~CAGLinkCtrl() -{ - -} - - -BEGIN_MESSAGE_MAP(CAGLinkCtrl, CStatic) - ON_WM_MOUSEMOVE() - ON_WM_SETCURSOR() - ON_WM_PAINT() - ON_WM_MOUSELEAVE() -END_MESSAGE_MAP() - - - -// CAGLinkCtrl Ϣ - -void CAGLinkCtrl::PreSubclassWindow() -{ - // We want to get mouse clicks via STN_CLICKED - DWORD dwStyle = GetStyle(); - ModifyStyle(0, SS_NOTIFY, 0); - - // Check that the window text isn't empty. If it is, set it as the URL. - - CStatic::PreSubclassWindow(); -} - - -void CAGLinkCtrl::OnMouseMove(UINT nFlags, CPoint point) -{ - // TODO: ڴϢ/Ĭֵ - if (!m_bOverControl){ - m_bOverControl = TRUE; - Invalidate(FALSE); - } - - if (!m_bTrackMouseEvent) { - TRACKMOUSEEVENT TrackMouseEvent; - TrackMouseEvent.cbSize = sizeof(TRACKMOUSEEVENT); - TrackMouseEvent.hwndTrack = GetSafeHwnd(); - TrackMouseEvent.dwFlags = TME_LEAVE; - TrackMouseEvent.dwHoverTime = HOVER_DEFAULT; - - m_bTrackMouseEvent = ::TrackMouseEvent(&TrackMouseEvent); - } - - CStatic::OnMouseMove(nFlags, point); -} - -void CAGLinkCtrl::OnPaint() -{ - CPaintDC dc(this); // device context for painting - // TODO: ڴ˴Ϣ - // ΪͼϢ CLinkCtrl::OnPaint() - - CString strWindowText; - CRect rcClient; - - GetClientRect(&rcClient); - - CFont *lpDefaultFont = dc.SelectObject(GetFont()); - dc.SetTextColor(m_crText); - dc.SetBkColor(m_crBack); - if (m_bOverControl) - dc.SetTextColor(m_crHover); - - GetWindowText(strWindowText); - dc.DrawText(strWindowText, &rcClient, DT_LEFT); - dc.SelectObject(lpDefaultFont); -} - - -BOOL CAGLinkCtrl::OnSetCursor(CWnd* pWnd, UINT nHitTest, UINT message) -{ - // TODO: ڴϢ/Ĭֵ - HCURSOR hLinkCursor = ::LoadCursor(NULL, IDC_HAND); - if (hLinkCursor != NULL) { - ::SetCursor(hLinkCursor); - return TRUE; - } - - return CStatic::OnSetCursor(pWnd, nHitTest, message); -} - -void CAGLinkCtrl::OnMouseLeave() -{ - // TODO: ڴϢ/Ĭֵ - m_bTrackMouseEvent = FALSE; - m_bOverControl = FALSE; - Invalidate(FALSE); - - CStatic::OnMouseLeave(); -} - -void CAGLinkCtrl::SetTextColor(COLORREF crText, COLORREF crHover) -{ - m_crText = crText; - m_crHover = crHover; -} - -void CAGLinkCtrl::SetBackColor(COLORREF crBack) -{ - m_crBack = crBack; -} - -COLORREF CAGLinkCtrl::GetTextColor() const -{ - return m_crText; -} - -COLORREF CAGLinkCtrl::GetHoverColor() const -{ - return m_crHover; -} \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGLinkCtrl.h b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGLinkCtrl.h deleted file mode 100644 index ae7a056d..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGLinkCtrl.h +++ /dev/null @@ -1,35 +0,0 @@ -#pragma once -#include - -// CAGLinkCtrl - -class CAGLinkCtrl : public CStatic -{ - DECLARE_DYNAMIC(CAGLinkCtrl) - -public: - CAGLinkCtrl(); - virtual ~CAGLinkCtrl(); - - void SetTextColor(COLORREF crText, COLORREF crHover); - void SetBackColor(COLORREF crBack); - COLORREF GetTextColor() const; - COLORREF GetHoverColor() const; - -protected: - virtual void PreSubclassWindow(); - - afx_msg void OnPaint(); - afx_msg void OnMouseMove(UINT nFlags, CPoint point); - afx_msg BOOL OnSetCursor(CWnd* pWnd, UINT nHitTest, UINT message); - afx_msg void OnMouseLeave(); - - DECLARE_MESSAGE_MAP() - -private: - COLORREF m_crText; - COLORREF m_crHover; // Hover colour - COLORREF m_crBack; - BOOL m_bOverControl; - BOOL m_bTrackMouseEvent; -}; \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGMessage.h b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGMessage.h deleted file mode 100644 index 8d5c5875..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGMessage.h +++ /dev/null @@ -1,9 +0,0 @@ -#pragma once - -#define WM_GOBACK WM_USER+100 -#define WM_GONEXT WM_USER+101 -#define WM_JOINCHANNEL WM_USER+200 -#define WM_LEAVECHANNEL WM_USER+201 - - -#define WM_AGSLD_TMBPOSCHANGED WM_USER+200 \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGResourceVisitor.cpp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGResourceVisitor.cpp deleted file mode 100644 index 201cecb0..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGResourceVisitor.cpp +++ /dev/null @@ -1,81 +0,0 @@ -#include "StdAfx.h" -#include "AGResourceVisitor.h" - -CAGResourceVisitor::CAGResourceVisitor(void) -{ -} - -CAGResourceVisitor::~CAGResourceVisitor(void) -{ -} - -BOOL PASCAL CAGResourceVisitor::SaveResourceToFile(LPCTSTR lpResourceType, WORD wResourceID, LPCTSTR lpFilePath) -{ - HMODULE hModule = ::GetModuleHandle(NULL); - - if(hModule == NULL) - return FALSE; - - HRSRC hResrc = ::FindResource(hModule, MAKEINTRESOURCE(wResourceID), lpResourceType); - if( hResrc == NULL) - return FALSE; - - HGLOBAL hGlobal = ::LoadResource(hModule, hResrc); - if( hGlobal == NULL ) - return FALSE; - - LPBYTE lpPointer = (LPBYTE)::LockResource( hGlobal ); - DWORD dwResSize = ::SizeofResource(hModule, hResrc); - - HANDLE hFile = ::CreateFile(lpFilePath, GENERIC_ALL, FILE_SHARE_READ, NULL, CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL); - if(hFile == INVALID_HANDLE_VALUE) - return FALSE; - - DWORD dwBytesWritten = 0; - ::WriteFile(hFile, lpPointer, dwResSize, &dwBytesWritten, NULL); - ::CloseHandle(hFile); - - return (dwBytesWritten == dwResSize) ? TRUE:FALSE; -} - -LPCSTR PASCAL CAGResourceVisitor::TransWinPathA(LPCSTR lpWinPath, LPSTR lpStandardPath, SIZE_T cchSize) -{ - int nPathLen = strlen(lpWinPath) + 1; - if(cchSize < nPathLen) - return NULL; - - CHAR szASIN[MAX_PATH]; - WCHAR szUnicode[MAX_PATH]; - - memset(szASIN, 0, MAX_PATH); - - for(int nIndex = 0; nIndex < nPathLen; nIndex++){ - - if(lpWinPath[nIndex] != '\\') - szASIN[nIndex] = lpWinPath[nIndex]; - else - szASIN[nIndex] = '/'; - } - - ::MultiByteToWideChar(CP_ACP, 0, szASIN, -1, szUnicode, MAX_PATH); - ::WideCharToMultiByte(CP_UTF8, 0, szUnicode, -1, lpStandardPath, cchSize, NULL, NULL); - return lpStandardPath; -} - -LPCWSTR PASCAL CAGResourceVisitor::TransWinPathW(LPCWSTR lpWinPath, LPWSTR lpStandardPath, SIZE_T cchSize) -{ - int nPathLen = wcslen(lpWinPath) + 1; - - if(cchSize < nPathLen) - return NULL; - - for(int nIndex = 0; nIndex < nPathLen; nIndex++){ - - if(lpWinPath[nIndex] != L'\\') - lpStandardPath[nIndex] = lpWinPath[nIndex]; - else - lpStandardPath[nIndex] = L'/'; - } - - return lpStandardPath; -} \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGResourceVisitor.h b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGResourceVisitor.h deleted file mode 100644 index 0483dc2d..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGResourceVisitor.h +++ /dev/null @@ -1,14 +0,0 @@ -#pragma once - -class CAGResourceVisitor -{ -public: - CAGResourceVisitor(void); - ~CAGResourceVisitor(void); - - static BOOL PASCAL SaveResourceToFile(LPCTSTR lpResourceType, WORD wResourceID, LPCTSTR lpFilePath); - - // ΪWINDOWS·Ŀ¼ָ׼ʽһ£תᷢ - static LPCSTR PASCAL TransWinPathA(LPCSTR lpWinPath, LPSTR lpStandardPath, SIZE_T cchSize); - static LPCWSTR PASCAL TransWinPathW(LPCWSTR lpWinPath, LPWSTR lpStandardPath, SIZE_T cchSize); -}; diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGScreenCaptureDlg.cpp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGScreenCaptureDlg.cpp deleted file mode 100644 index 21b3c91a..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGScreenCaptureDlg.cpp +++ /dev/null @@ -1,210 +0,0 @@ -// AGScreenCaptureWnd.cpp : ʵļ -// - -#include "stdafx.h" -#include "OpenVideoCall.h" -#include "AGScreenCaptureDlg.h" - - -// CAGScreenCaptureWnd - -IMPLEMENT_DYNAMIC(CAGScreenCaptureDlg, CDialogEx) - -CAGScreenCaptureDlg::CAGScreenCaptureDlg(CWnd* pParent) - : m_hMarkWnd(NULL) -{ - -} - -CAGScreenCaptureDlg::~CAGScreenCaptureDlg() -{ -} - - -BEGIN_MESSAGE_MAP(CAGScreenCaptureDlg, CDialogEx) - ON_WM_MOUSEMOVE() - ON_WM_PAINT() - ON_WM_ERASEBKGND() - ON_WM_SHOWWINDOW() - ON_WM_LBUTTONDBLCLK() - ON_WM_RBUTTONDOWN() -END_MESSAGE_MAP() - - - -// CAGScreenCaptureWnd Ϣ -int CAGScreenCaptureDlg::RefreashWndInfo() -{ - m_listWnd.RemoveAll(); - ::EnumWindows(&CAGScreenCaptureDlg::WndEnumProc, (LPARAM)&m_listWnd); - - return static_cast(m_listWnd.GetCount()); -} - -BOOL CAGScreenCaptureDlg::SaveScreen(LPCRECT lpRect) -{ - CDC dcDesktop; - CRect rcDesktop; - CRect rcDest; - - CBitmap *lpOldBitmap = NULL; - - CWnd *lpWndDesktop = GetDesktopWindow(); - CDC *lpDCDesktop = lpWndDesktop->GetDC(); - - lpWndDesktop->GetWindowRect(&rcDesktop); - - if (lpRect == NULL) - rcDest.CopyRect(&rcDesktop); - else { - if (lpRect->left < rcDesktop.left || lpRect->top < rcDesktop.top || lpRect->right > rcDesktop.right || lpRect->bottom > rcDesktop.bottom) - return FALSE; - else - rcDest.CopyRect(lpRect); - } - - dcDesktop.CreateCompatibleDC(lpDCDesktop); - - if (m_bmpDesktop.GetSafeHandle() != NULL) - m_bmpDesktop.DeleteObject(); - - m_bmpDesktop.CreateCompatibleBitmap(lpDCDesktop, rcDest.Width(), rcDest.Height()); - lpOldBitmap = dcDesktop.SelectObject(&m_bmpDesktop); - dcDesktop.BitBlt(0, 0, rcDesktop.Width(), rcDesktop.Height(), lpDCDesktop, 0, 0, SRCCOPY); - dcDesktop.SelectObject(lpOldBitmap); - - return TRUE; -} - -void CAGScreenCaptureDlg::OnMouseMove(UINT nFlags, CPoint point) -{ - // TODO: ڴϢ/Ĭֵ - POSITION pos = m_listWnd.GetHeadPosition(); - CRect rcMarkWnd; - HWND hMarkWnd = NULL; - HWND hFound = NULL; - - while (pos != NULL) { - hFound = m_listWnd.GetNext(pos); - ::GetWindowRect(hFound, &rcMarkWnd); - if (rcMarkWnd.PtInRect(point)) { - hMarkWnd = hFound; - break; - } - } - - if (hMarkWnd != m_hMarkWnd) { - m_hMarkWnd = hMarkWnd; - Invalidate(); - } - - CDialogEx::OnMouseMove(nFlags, point); -} - - -void CAGScreenCaptureDlg::OnPaint() -{ - CPaintDC dc(this); - CDC dcBuffer; - CBitmap bmpBuffer; - // TODO: ڴ˴Ϣ - // ΪͼϢ CWnd::OnPaint() - CRect rcWindow; - BLENDFUNCTION blend; - GetWindowRect(&rcWindow); - - CBrush brBack; - brBack.CreateSolidBrush(RGB(0x00, 0x00, 0x00)); - dcBuffer.CreateCompatibleDC(&dc); - bmpBuffer.CreateCompatibleBitmap(&dc, rcWindow.Width(), rcWindow.Height()); - - CBitmap *lpOldBitmap = dcBuffer.SelectObject(&bmpBuffer); - dcBuffer.FillRect(&rcWindow, &brBack); - - blend.BlendOp = AC_SRC_OVER; - blend.AlphaFormat = 0; - blend.SourceConstantAlpha = 0x80; - blend.BlendFlags = 0; - - dc.AlphaBlend(0, 0, rcWindow.Width(), rcWindow.Height(), &dcBuffer, 0, 0, rcWindow.Width(), rcWindow.Height(), blend); - - if (m_hMarkWnd != NULL) { - CRect rcMarkWnd; - CDC dcBitmap; - CPen penMark; - CString strTip; - - penMark.CreatePen(PS_SOLID, 4, RGB(0x00, 0xA0, 0xE9)); - ::GetWindowRect(m_hMarkWnd, &rcMarkWnd); - dcBitmap.CreateCompatibleDC(&dc); - dcBitmap.SelectObject(&m_bmpDesktop); - dc.BitBlt(rcMarkWnd.left, rcMarkWnd.top, rcMarkWnd.Width(), rcMarkWnd.Height(), &dcBitmap, rcMarkWnd.left, rcMarkWnd.top, SRCCOPY); - - dc.SelectObject(&penMark); - dc.SelectStockObject(NULL_BRUSH); - dc.Rectangle(&rcMarkWnd); - - strTip = _T("double click to share this window or ESC to abort"); -// dc.SetBkMode(TRANSPARENT); - dc.SetBkColor(RGB(0x00, 0xA0, 0xE9)); - dc.SetTextColor(RGB(0xFF, 0xFF, 0xFF)); - dc.TextOut(rcMarkWnd.left + 10, rcMarkWnd.top+10, strTip); - } -} - - -BOOL CALLBACK CAGScreenCaptureDlg::WndEnumProc(HWND hWnd, LPARAM lParam) -{ - CList *lpListctrl = (CList *)lParam; - - LONG lStyle = ::GetWindowLong(hWnd, GWL_STYLE); - - if ((lStyle&WS_VISIBLE) != 0 && (lStyle&(WS_POPUP | WS_SYSMENU)) != 0) - lpListctrl->AddTail(hWnd); - - return TRUE; -} - - -BOOL CAGScreenCaptureDlg::OnEraseBkgnd(CDC* pDC) -{ - // TODO: ڴϢ/Ĭֵ - CDC dcBuffer; - dcBuffer.CreateCompatibleDC(pDC); - dcBuffer.SelectObject(&m_bmpDesktop); - - CRect rcWindow; - GetWindowRect(&rcWindow); - pDC->BitBlt(0, 0, rcWindow.Width(), rcWindow.Height(), &dcBuffer, 0, 0, SRCCOPY); - - return TRUE; -} - - -void CAGScreenCaptureDlg::OnShowWindow(BOOL bShow, UINT nStatus) -{ - CDialogEx::OnShowWindow(bShow, nStatus); - - // TODO: ڴ˴Ϣ -// if (!bShow) -// m_bmpDesktop.DeleteObject(); - -} - - -void CAGScreenCaptureDlg::OnLButtonDblClk(UINT nFlags, CPoint point) -{ - // TODO: ڴϢ/Ĭֵ - GetParent()->SendMessage(WM_WINDOWSHARE, (WPARAM)m_hMarkWnd, 0); -// CDialogEx::OnLButtonDblClk(nFlags, point); - CDialogEx::OnOK(); -} - - -void CAGScreenCaptureDlg::OnRButtonDown(UINT nFlags, CPoint point) -{ - // TODO: ڴϢ/Ĭֵ - -// CDialogEx::OnRButtonDown(nFlags, point); - CDialogEx::OnOK(); -} diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGScreenCaptureDlg.h b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGScreenCaptureDlg.h deleted file mode 100644 index c5efb7ed..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGScreenCaptureDlg.h +++ /dev/null @@ -1,43 +0,0 @@ -#pragma once -#include "afxcoll.h" - -#define WM_WINDOWSHARE WM_USER+303 -// CAGScreenCaptureWnd - -class CAGScreenCaptureDlg : public CDialogEx -{ - DECLARE_DYNAMIC(CAGScreenCaptureDlg) - -public: - CAGScreenCaptureDlg(CWnd* pParent = NULL); - virtual ~CAGScreenCaptureDlg(); - - enum { IDD = IDD_SCRCAP_DIALOG }; - - int RefreashWndInfo(); - BOOL SaveScreen(LPCRECT lpRect); - -protected: - afx_msg void OnMouseMove(UINT nFlags, CPoint point); - afx_msg void OnPaint(); - - afx_msg BOOL OnEraseBkgnd(CDC* pDC); - afx_msg void OnShowWindow(BOOL bShow, UINT nStatus); - - DECLARE_MESSAGE_MAP() - - static BOOL CALLBACK WndEnumProc(HWND hWnd, LPARAM lParam); - -private: - CBitmap m_bmpDesktop; - - CList m_listWnd; - HWND m_hMarkWnd; - -public: - - afx_msg void OnLButtonDblClk(UINT nFlags, CPoint point); - afx_msg void OnRButtonDown(UINT nFlags, CPoint point); -}; - - diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGSliderCtrl.cpp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGSliderCtrl.cpp deleted file mode 100644 index 1b5cdfae..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGSliderCtrl.cpp +++ /dev/null @@ -1,202 +0,0 @@ -// AGSliderCtrl.cpp : ʵļ -// - -#include "stdafx.h" -#include "AGSliderCtrl.h" - - -// CAGSliderCtrl - -IMPLEMENT_DYNAMIC(CAGSliderCtrl, CSliderCtrl) - -CAGSliderCtrl::CAGSliderCtrl() -: m_dwChannelHeight(2) -, m_nThumbHeight(0) -, m_nThumbWidth(0) -, m_bHover(FALSE) -{ - m_brChannel.CreateSolidBrush(RGB(0xC8, 0xC8, 0xC8)); - m_brChannelHot.CreateSolidBrush(RGB(0x00, 0xA0, 0xEB)); - m_brBack.CreateSolidBrush(RGB(0xFF, 0xFF, 0xFF)); -} - -CAGSliderCtrl::~CAGSliderCtrl() -{ - m_brChannel.DeleteObject(); - m_brChannelHot.DeleteObject(); - m_brBack.DeleteObject(); -} - - -BEGIN_MESSAGE_MAP(CAGSliderCtrl, CSliderCtrl) - ON_NOTIFY_REFLECT(NM_CUSTOMDRAW, &CAGSliderCtrl::OnNMCustomdraw) - ON_WM_MOUSEMOVE() - ON_WM_MOUSELEAVE() -END_MESSAGE_MAP() - - - -// CAGSliderCtrl Ϣ -BOOL CAGSliderCtrl::SetThumbBitmap(UINT nIDNormal, UINT nIDHover, UINT nIDPush, COLORREF crMaskColor) -{ - CBitmap bmpMap; - BITMAP bmpInfo; - BOOL bSuccess = FALSE; - - bSuccess = bmpMap.LoadBitmap(nIDNormal); - if (!bSuccess) - return FALSE; - - bmpMap.GetBitmap(&bmpInfo); - m_imgThumb.DeleteImageList(); - m_imgThumb.Create(bmpInfo.bmWidth, bmpInfo.bmHeight, ILC_COLOR24 | ILC_MASK, 3, 1); - m_nThumbHeight = bmpInfo.bmHeight; - m_nThumbWidth = bmpInfo.bmWidth; - - m_imgThumb.Add(&bmpMap, crMaskColor); - if (nIDHover != 0) { - bmpMap.DeleteObject(); - bSuccess = bmpMap.LoadBitmap(nIDHover); - } - - if (bSuccess) - m_imgThumb.Add(&bmpMap, crMaskColor); - if (nIDPush != 0) { - bmpMap.DeleteObject(); - bSuccess = bmpMap.LoadBitmap(nIDPush); - } - - if (bSuccess) - m_imgThumb.Add(&bmpMap, crMaskColor); - - bmpMap.DeleteObject(); - - return bSuccess; -} - -BOOL CAGSliderCtrl::SetChannelColor(COLORREF crNormal, COLORREF crHot) -{ - m_brChannel.DeleteObject(); - m_brChannelHot.DeleteObject(); - - m_brChannel.CreateSolidBrush(crNormal); - m_brChannelHot.CreateSolidBrush(crHot); - - return TRUE; -} -BOOL CAGSliderCtrl::SetBkColor(COLORREF crBkColor) -{ - m_brBack.DeleteObject(); - - return m_brBack.CreateSolidBrush(crBkColor); -} - -void CAGSliderCtrl::OnNMCustomdraw(NMHDR *pNMHDR, LRESULT *pResult) -{ - LPNMCUSTOMDRAW lpCustomDraw = (LPNMCUSTOMDRAW)pNMHDR; - CDC *pDC = CDC::FromHandle(lpCustomDraw->hdc); - - switch (lpCustomDraw->dwDrawStage) - { - case CDDS_PREPAINT: - *pResult = CDRF_NOTIFYITEMDRAW; - break; - case CDDS_ITEMPREPAINT: - { - switch (lpCustomDraw->dwItemSpec) - { - case TBCD_TICS: - *pResult = CDRF_DODEFAULT; - break; - case TBCD_THUMB: - *pResult = OnDrawThumb(pDC, lpCustomDraw); - break; - case TBCD_CHANNEL: - *pResult = OnDrawChannel(pDC, lpCustomDraw); - break; - } - break; - } - } -} - -LRESULT CAGSliderCtrl::OnDrawThumb(CDC *pDC, LPNMCUSTOMDRAW lpCustomDraw) -{ - if (m_imgThumb.GetSafeHandle() == NULL || m_imgThumb.GetImageCount() == 0) - return CDRF_DODEFAULT; - - CRect rcThumb; - GetThumbRect(&rcThumb); - CPoint ptThumb = rcThumb.CenterPoint(); - ptThumb.Offset(-m_nThumbWidth/2, -m_nThumbHeight/2); - - if ( (lpCustomDraw->uItemState&CDIS_SELECTED) || m_bHover ) - m_imgThumb.Draw(pDC, 2, ptThumb, ILD_NORMAL); - else - m_imgThumb.Draw(pDC, 0, ptThumb, ILD_NORMAL); - - Invalidate(FALSE); - lpCustomDraw->rc.left = ptThumb.x; - lpCustomDraw->rc.top = ptThumb.y; - lpCustomDraw->rc.right = ptThumb.x + m_nThumbWidth; - lpCustomDraw->rc.right = ptThumb.y + m_nThumbHeight; - - return CDRF_SKIPDEFAULT; -} - -LRESULT CAGSliderCtrl::OnDrawChannel(CDC *pDC, LPNMCUSTOMDRAW lpCustomDraw) -{ - CRect rcThumb; - CRect rcChannel; - CRect rcDraw; - - GetClientRect(&rcDraw); - GetThumbRect(&rcThumb); - GetChannelRect(&rcChannel); - - pDC->FillRect(&rcDraw, &m_brBack); - - rcChannel.top = rcThumb.CenterPoint().y - m_dwChannelHeight / 2; - rcChannel.bottom = rcThumb.CenterPoint().y + m_dwChannelHeight / 2; - - rcDraw.CopyRect(&rcChannel); - rcDraw.right = rcThumb.left; - pDC->FillRect(&rcDraw, &m_brChannelHot); - - rcDraw.CopyRect(&rcChannel); - rcDraw.left = rcThumb.right; - pDC->FillRect(&rcDraw, &m_brChannel); - - return CDRF_SKIPDEFAULT; -} - - -void CAGSliderCtrl::OnMouseMove(UINT nFlags, CPoint point) -{ - // TODO: ڴϢ/Ĭֵ - CRect rcThumbRect; - BOOL bLastState = m_bHover; - - GetThumbRect(&rcThumbRect); - if (rcThumbRect.PtInRect(point)) - m_bHover = TRUE; - else - m_bHover = FALSE; - - if (bLastState != m_bHover) - InvalidateRect(rcThumbRect); - - CSliderCtrl::OnMouseMove(nFlags, point); -} - -void CAGSliderCtrl::OnMouseLeave() -{ - // TODO: ڴϢ/Ĭֵ - m_bHover = FALSE; - - CRect rcThumb; - GetThumbRect(&rcThumb); - InvalidateRect(rcThumb); - - CSliderCtrl::OnMouseLeave(); -} \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGSliderCtrl.h b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGSliderCtrl.h deleted file mode 100644 index df5c3faa..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGSliderCtrl.h +++ /dev/null @@ -1,45 +0,0 @@ -#pragma once - - - -// CAGSliderCtrl - -class CAGSliderCtrl : public CSliderCtrl -{ - DECLARE_DYNAMIC(CAGSliderCtrl) - -public: - CAGSliderCtrl(); - virtual ~CAGSliderCtrl(); - - BOOL SetThumbBitmap(UINT nIDNormal, UINT nIDHover = 0, UINT nIDPush = 0, COLORREF crMaskColor = RGB(0xFF, 0, 0xFF)); - BOOL SetChannelColor(COLORREF crNormal = RGB(0xC8, 0xC8, 0xC8), COLORREF crHot = RGB(0x00, 0xA0, 0xEB)); - BOOL SetChannelHeight(DWORD dwChannelHeight = 2); - BOOL SetBkColor(COLORREF crBkColor = RGB(0xFF, 0xFF, 0xFF)); - -protected: - afx_msg void OnNMCustomdraw(NMHDR *pNMHDR, LRESULT *pResult); - afx_msg void OnMouseMove(UINT nFlags, CPoint point); - afx_msg void OnMouseLeave(); - - DECLARE_MESSAGE_MAP() - -protected: - LRESULT OnDrawThumb(CDC *pDC, LPNMCUSTOMDRAW lpCustomDraw); - LRESULT OnDrawChannel(CDC *pDC, LPNMCUSTOMDRAW lpCustomDraw); - -private: - CImageList m_imgThumb; - - CBrush m_brBack; - CBrush m_brChannel; - CBrush m_brChannelHot; - - DWORD m_dwChannelHeight; - int m_nThumbHeight; - int m_nThumbWidth; - - BOOL m_bHover; -}; - - diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGVideoTestWnd.cpp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGVideoTestWnd.cpp deleted file mode 100644 index db024c5e..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGVideoTestWnd.cpp +++ /dev/null @@ -1,114 +0,0 @@ -// AGVideoTestWnd.cpp : ʵļ -// - -#include "stdafx.h" -#include "OpenVideoCall.h" -#include "AGVideoTestWnd.h" - - -// CAGVideoTestWnd - -IMPLEMENT_DYNAMIC(CAGVideoTestWnd, CWnd) - -CAGVideoTestWnd::CAGVideoTestWnd() -: m_nVolRange(255) -, m_nCurVol(0) -, m_crVolbarFreeColor(RGB(32, 32, 32)) -, m_crVolbarBusyColor(RGB(208, 208, 208)) -, m_crVolbarBackColor(RGB(0x26, 0x26, 0x26)) -, m_crBackColor(RGB(0x70, 0x70, 0x70)) -, m_nVolbarWidth(15) -{ - -} - -CAGVideoTestWnd::~CAGVideoTestWnd() -{ -} - - -BEGIN_MESSAGE_MAP(CAGVideoTestWnd, CWnd) - ON_WM_PAINT() - ON_WM_CREATE() - ON_WM_SIZE() -END_MESSAGE_MAP() - - - -// CAGVideoTestWnd Ϣ - -int CAGVideoTestWnd::OnCreate(LPCREATESTRUCT lpCreateStruct) -{ - if (CWnd::OnCreate(lpCreateStruct) == -1) - return -1; - - // TODO: ڴרõĴ - CRect rcChildRect; - - DWORD dwWndStyle = WS_VISIBLE | WS_CHILD; - rcChildRect.SetRect(15, 0, lpCreateStruct->cx-30, lpCreateStruct->cy); - m_wndVideoWnd.Create(NULL, _T("AgoraVideoWnd"), dwWndStyle, rcChildRect, this, IDC_STATIC); - - return 0; -} - -void CAGVideoTestWnd::OnPaint() -{ - // TODO: ڴ˴Ϣ - // ΪͼϢ CWnd::OnPaint() - CPaintDC dc(this); - - CRect rcClient; - - GetClientRect(&rcClient); - dc.FillSolidRect(0, 0, rcClient.Width(), rcClient.Height(), m_crBackColor); - - dc.FillSolidRect(0, 0, m_nVolbarWidth, rcClient.Height(), m_crVolbarBackColor); - dc.FillSolidRect(rcClient.Width() - m_nVolbarWidth, 0, m_nVolbarWidth, rcClient.Height(), m_crVolbarBackColor); - - int nMarkCount = rcClient.Height() / 5; - int nTopPoint = m_nCurVol*nMarkCount / m_nVolRange; - - for (int nIndex = 0; nIndex < nMarkCount; nIndex++) { - if (nIndex <= nTopPoint) { - dc.FillSolidRect(0, rcClient.bottom - 5 * nIndex - 3, m_nVolbarWidth, 3, m_crVolbarBusyColor); - dc.FillSolidRect(rcClient.Width() - m_nVolbarWidth, rcClient.bottom - 5 * nIndex - 3, m_nVolbarWidth, 3, m_crVolbarBusyColor); - } - else { - dc.FillSolidRect(0, rcClient.bottom - 5 * nIndex - 3, m_nVolbarWidth, 3, m_crVolbarFreeColor); - dc.FillSolidRect(rcClient.Width() - m_nVolbarWidth, rcClient.bottom - 5 * nIndex - 3, m_nVolbarWidth, 3, m_crVolbarFreeColor); - } - } -} - - -void CAGVideoTestWnd::SetVolRange(int nRange) -{ - if (nRange > 100 || nRange < 0) - nRange = 100; - - m_nVolRange = nRange; - - Invalidate(FALSE); -} - -void CAGVideoTestWnd::SetCurVol(int nCurVol) -{ - if (nCurVol < 0 || nCurVol > m_nVolRange) - nCurVol = 0; - - m_nCurVol = nCurVol; - - InvalidateRect(FALSE); -} - - -void CAGVideoTestWnd::OnSize(UINT nType, int cx, int cy) -{ - CWnd::OnSize(nType, cx, cy); - - if (m_wndVideoWnd.GetSafeHwnd() != NULL) - m_wndVideoWnd.MoveWindow(15, 0, cx - 30, cy); - - // TODO: ڴ˴Ϣ -} diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGVideoTestWnd.h b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGVideoTestWnd.h deleted file mode 100644 index 8d2a7fa7..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGVideoTestWnd.h +++ /dev/null @@ -1,45 +0,0 @@ -#pragma once - - -// CAGVideoTestWnd - -class CAGVideoTestWnd : public CWnd -{ - DECLARE_DYNAMIC(CAGVideoTestWnd) - -public: - CAGVideoTestWnd(); - virtual ~CAGVideoTestWnd(); - - HWND GetVideoSafeHwnd() { return m_wndVideoWnd.GetSafeHwnd(); }; - - // ָʾ - - void SetVolbarColor(DWORD dwFreeColor = RGB(184, 184, 184), DWORD dwBusyColor = RGB(0, 255, 0), DWORD dwBackColor = RGB(0, 0, 0)); // 趨ɫ - void SetVolRange(int nRange = 100); - void SetCurVol(int nCurVol = 0); - -protected: - afx_msg void OnPaint(); - afx_msg int OnCreate(LPCREATESTRUCT lpCreateStruct); - - DECLARE_MESSAGE_MAP() - -private: - CWnd m_wndVideoWnd; // the wnd for show video - - int m_nVolbarWidth; - - int m_nVolbarPos; // the vol bar pos - int m_nVolRange; // the max vol - int m_nCurVol; // the current vol - - COLORREF m_crBackColor; - COLORREF m_crVolbarFreeColor; - COLORREF m_crVolbarBusyColor; - COLORREF m_crVolbarBackColor; -public: - afx_msg void OnSize(UINT nType, int cx, int cy); -}; - - diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGVideoWnd.cpp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGVideoWnd.cpp deleted file mode 100644 index 7ea120e2..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGVideoWnd.cpp +++ /dev/null @@ -1,357 +0,0 @@ -// AGVideoWnd.cpp : ʵļ -// - -#include "stdafx.h" -#include "OpenVideoCall.h" -#include "AGVideoWnd.h" - -IMPLEMENT_DYNAMIC(CAGInfoWnd, CWnd) - -CAGInfoWnd::CAGInfoWnd() -: m_bShowTip(TRUE) -, m_nWidth(0) -, m_nHeight(0) -, m_nFps(0) -, m_nBitrate(0) -{ - m_brBack.CreateSolidBrush(RGB(0x00, 0xA0, 0xE9)); -} - -CAGInfoWnd::~CAGInfoWnd() -{ - m_brBack.DeleteObject(); -} - - -BEGIN_MESSAGE_MAP(CAGInfoWnd, CWnd) - ON_WM_PAINT() - ON_WM_ERASEBKGND() -END_MESSAGE_MAP() - - -void CAGInfoWnd::ShowTips(BOOL bShow) -{ - m_bShowTip = bShow; - - if (bShow) - ShowWindow(SW_SHOW); - else - ShowWindow(SW_HIDE); - - Invalidate(FALSE); -} - -void CAGInfoWnd::SetVideoResolution(int nWidth, int nHeight) -{ - m_nWidth = nWidth; - m_nHeight = nHeight; - - if (m_bShowTip) { - Invalidate(TRUE); - UpdateWindow(); - } -} - -void CAGInfoWnd::SetFrameRateInfo(int nFPS) -{ - m_nFps = nFPS; - - if (m_bShowTip) { - Invalidate(TRUE); - UpdateWindow(); - } -} - -void CAGInfoWnd::SetBitrateInfo(int nBitrate) -{ - m_nBitrate = nBitrate; - - if (m_bShowTip) { - Invalidate(TRUE); - UpdateWindow(); - } -} - -void CAGInfoWnd::OnPaint() -{ - CPaintDC dc(this); - CRect rcClient; - CString strTip; - - dc.SetBkMode(TRANSPARENT); - dc.SetTextColor(RGB(0xFF, 0xFF, 0xFF)); - - if (m_bShowTip) { - // 640x480,15fps,400k - GetClientRect(&rcClient); - rcClient.top += 4; - strTip.Format(_T("%dx%d, %dfps, %dK"), m_nWidth, m_nHeight, m_nFps, m_nBitrate); - dc.DrawText(strTip, &rcClient, DT_VCENTER | DT_CENTER); - } -} - -BOOL CAGInfoWnd::OnEraseBkgnd(CDC* pDC) -{ - // TODO: ڴϢ/Ĭֵ - CRect rcClient; - - GetClientRect(&rcClient); - pDC->FillRect(&rcClient, &m_brBack); - - return TRUE; -} - -// CAGVideoWnd - -IMPLEMENT_DYNAMIC(CAGVideoWnd, CWnd) - -CAGVideoWnd::CAGVideoWnd() -: m_nUID(0) -, m_crBackColor(RGB(0x58, 0x58, 0x58)) -, m_bShowVideoInfo(FALSE) -, m_bBigShow(FALSE) -, m_bBackground(FALSE) -{ - -} - -CAGVideoWnd::~CAGVideoWnd() -{ - m_imgBackGround.DeleteImageList(); -} - - -BEGIN_MESSAGE_MAP(CAGVideoWnd, CWnd) - ON_WM_ERASEBKGND() - ON_WM_LBUTTONDOWN() - ON_WM_RBUTTONDOWN() - ON_WM_CREATE() - ON_WM_PAINT() - ON_WM_SIZE() - ON_WM_LBUTTONDBLCLK() - ON_WM_PAINT() -END_MESSAGE_MAP() - - - -// CAGVideoWnd Ϣ -BOOL CAGVideoWnd::OnEraseBkgnd(CDC* pDC) -{ - // TODO: ڴϢ/Ĭֵ - CRect rcClient; - CPoint ptDraw; - IMAGEINFO imgInfo; - - GetClientRect(&rcClient); - - pDC->FillSolidRect(&rcClient, m_crBackColor); - if (!m_imgBackGround.GetImageInfo(0, &imgInfo)) - return TRUE; - - ptDraw.SetPoint((rcClient.Width() - imgInfo.rcImage.right) / 2, (rcClient.Height() - imgInfo.rcImage.bottom) / 2); - if (ptDraw.x < 0) - ptDraw.x = 0; - if (ptDraw.y <= 0) - ptDraw.y = 0; - - m_imgBackGround.Draw(pDC, 0, ptDraw, ILD_NORMAL); - return TRUE; -} - -void CAGVideoWnd::SetUID(UINT nUID) -{ - m_nUID = nUID; - - if (m_nUID == 0) - m_wndInfo.ShowWindow(SW_HIDE); - else - m_wndInfo.ShowWindow(SW_SHOW); -} - -UINT CAGVideoWnd::GetUID() -{ - return m_nUID; -} - -BOOL CAGVideoWnd::IsWndFree() -{ - return m_nUID == 0 ? TRUE : FALSE; -} - -BOOL CAGVideoWnd::SetBackImage(UINT nID, UINT nWidth, UINT nHeight, COLORREF crMask) -{ - CBitmap bmBackImage; - - if (!bmBackImage.LoadBitmap(nID)) - return FALSE; - - m_imgBackGround.DeleteImageList(); - - m_imgBackGround.Create(nWidth, nHeight, ILC_COLOR24 | ILC_MASK, 1, 1); - m_imgBackGround.Add(&bmBackImage, crMask); - bmBackImage.DeleteObject(); - - Invalidate(TRUE); - - return TRUE; -} - -void CAGVideoWnd::ShowBackground(BOOL bBackground) -{ - m_bBackground = bBackground; - - Invalidate(TRUE); -} - -void CAGVideoWnd::SetFaceColor(COLORREF crBackColor) -{ - m_crBackColor = crBackColor; - - Invalidate(TRUE); -} - -void CAGVideoWnd::SetVideoResolution(UINT nWidth, UINT nHeight) -{ - m_nWidth = nWidth; - m_nHeight = nHeight; - - m_wndInfo.SetVideoResolution(nWidth, nHeight); -} - -void CAGVideoWnd::GetVideoResolution(UINT *nWidth, UINT *nHeight) -{ - *nWidth = m_nWidth; - *nHeight = m_nHeight; -} - -void CAGVideoWnd::SetBitrateInfo(int nReceivedBitrate) -{ - m_nBitRate = nReceivedBitrate; - m_wndInfo.SetBitrateInfo(nReceivedBitrate); -} - -void CAGVideoWnd::SetFrameRateInfo(int nReceiveFrameRate) -{ - m_nFrameRate = nReceiveFrameRate; - m_wndInfo.SetFrameRateInfo(nReceiveFrameRate); -} - -void CAGVideoWnd::OnLButtonDown(UINT nFlags, CPoint point) -{ - // TODO: ڴϢ/Ĭֵ - - ::SendMessage(GetParent()->GetSafeHwnd(), WM_SHOWBIG, (WPARAM)this, (LPARAM)m_nUID); - - CWnd::OnLButtonDown(nFlags, point); -} - - -void CAGVideoWnd::OnRButtonDown(UINT nFlags, CPoint point) -{ - // TODO: ڴϢ/Ĭֵ - ::SendMessage(GetParent()->GetSafeHwnd(), WM_SHOWMODECHANGED, (WPARAM)this, (LPARAM)m_nUID); - - CWnd::OnRButtonDown(nFlags, point); -} - - -int CAGVideoWnd::OnCreate(LPCREATESTRUCT lpCreateStruct) -{ - if (CWnd::OnCreate(lpCreateStruct) == -1) - return -1; - - // TODO: ڴרõĴ - m_wndInfo.Create(NULL, NULL, WS_CHILD | WS_VISIBLE, CRect(0, 0, 192, 28), this, IDC_STATIC); - - return 0; -} - - -void CAGVideoWnd::ShowVideoInfo(BOOL bShow) -{ - m_bShowVideoInfo = bShow; - - m_wndInfo.ShowTips(bShow); - Invalidate(TRUE); - -/* if (!bShow) { - CRect rcTip; - m_wndInfo.GetWindowRect(&rcTip); - - } - */ - -} - -void CAGVideoWnd::SetBigShowFlag(BOOL bBigShow) -{ - CRect rcClient; - - m_bBigShow = bBigShow; - GetClientRect(&rcClient); - - int x = (rcClient.Width()- 192) / 2; - int y = rcClient.Height() - 24; - - if (m_wndInfo.GetSafeHwnd() != NULL) { - if (m_bBigShow) - y -= 4; - - m_wndInfo.MoveWindow(x, y, 192, 24); - } -}; - - -void CAGVideoWnd::OnSize(UINT nType, int cx, int cy) -{ - CWnd::OnSize(nType, cx, cy); - - int x = (cx - 192) / 2; - int y = cy - 24; - // TODO: ڴ˴Ϣ - if (m_wndInfo.GetSafeHwnd() != NULL) { - if (m_bBigShow) - y -= 4; - - m_wndInfo.MoveWindow(x, y, 192, 24); - } -} - - -void CAGVideoWnd::OnLButtonDblClk(UINT nFlags, CPoint point) -{ - // TODO: ڴϢ/Ĭֵ - ::SendMessage(GetParent()->GetSafeHwnd(), WM_SHOWMODECHANGED, (WPARAM)this, (LPARAM)m_nUID); - - CWnd::OnLButtonDblClk(nFlags, point); -} - - -void CAGVideoWnd::OnPaint() -{ - CPaintDC dc(this); // device context for painting - // TODO: ڴ˴Ϣ - // ΪͼϢ CWnd::OnPaint() - - if (m_bBackground) { - CRect rcClient; - CPoint ptDraw; - IMAGEINFO imgInfo; - - GetClientRect(&rcClient); - - dc.FillSolidRect(&rcClient, m_crBackColor); - if (!m_imgBackGround.GetImageInfo(0, &imgInfo)) - return; - - ptDraw.SetPoint((rcClient.Width() - imgInfo.rcImage.right) / 2, (rcClient.Height() - imgInfo.rcImage.bottom) / 2); - if (ptDraw.x < 0) - ptDraw.x = 0; - if (ptDraw.y <= 0) - ptDraw.y = 0; - - m_imgBackGround.Draw(&dc, 0, ptDraw, ILD_NORMAL); - } - else - return CWnd::OnPaint(); -} diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGVideoWnd.h b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGVideoWnd.h deleted file mode 100644 index 8809da9b..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AGVideoWnd.h +++ /dev/null @@ -1,104 +0,0 @@ -#pragma once - -#define WM_SHOWMODECHANGED WM_USER+300 -#define WM_SHOWBIG WM_USER+301 - -class CAGInfoWnd : public CWnd -{ - DECLARE_DYNAMIC(CAGInfoWnd) - -public: - CAGInfoWnd(); - virtual ~CAGInfoWnd(); - - void ShowTips(BOOL bShow = TRUE); - void SetVideoResolution(int nWidth, int nHeight); - void SetFrameRateInfo(int nFPS); - void SetBitrateInfo(int nBitrate); - -protected: - afx_msg void OnPaint(); - afx_msg BOOL OnEraseBkgnd(CDC* pDC); - - DECLARE_MESSAGE_MAP() - -private: - BOOL m_bShowTip; - - COLORREF m_crBackColor; - - int m_nWidth; - int m_nHeight; - int m_nFps; - int m_nBitrate; - - CBrush m_brBack; -}; - - -class CAGVideoWnd : public CWnd -{ - DECLARE_DYNAMIC(CAGVideoWnd) - -public: - CAGVideoWnd(); - virtual ~CAGVideoWnd(); - - void SetUID(UINT dwUID); - - UINT GetUID(); - BOOL IsWndFree(); - - void SetFaceColor(COLORREF crBackColor); - BOOL SetBackImage(UINT nID, UINT nWidth, UINT nHeight, COLORREF crMask = RGB(0xFF, 0xff, 0xFF)); - - void ShowBackground(BOOL bBackground); - BOOL IsBackgroundMode() { return m_bBackground; }; - - void SetVideoResolution(UINT nWidth, UINT nHeight); - void GetVideoResolution(UINT *nWidth, UINT *nHeight); - - void SetBitrateInfo(int nReceivedBitrate); - int GetBitrateInfo() { return m_nBitRate; }; - - void SetFrameRateInfo(int nReceiveFrameRate); - int GetFrameRateInfo() { return m_nFrameRate; }; - - void ShowVideoInfo(BOOL bShow); - BOOL IsVideoInfoShowed() { return m_bShowVideoInfo; }; - - void SetBigShowFlag(BOOL bBigShow); - BOOL IsBigShow() { return m_bBigShow; }; - -protected: - afx_msg int OnCreate(LPCREATESTRUCT lpCreateStruct); - afx_msg BOOL OnEraseBkgnd(CDC* pDC); - afx_msg void OnLButtonDown(UINT nFlags, CPoint point); - afx_msg void OnLButtonDblClk(UINT nFlags, CPoint point); - afx_msg void OnRButtonDown(UINT nFlags, CPoint point); - afx_msg void OnSize(UINT nType, int cx, int cy); - - DECLARE_MESSAGE_MAP() - -private: - CImageList m_imgBackGround; - COLORREF m_crBackColor; - - CAGInfoWnd m_wndInfo; - -private: - UINT m_nUID; - - UINT m_nWidth; - UINT m_nHeight; - int m_nFrameRate; - int m_nBitRate; - BOOL m_bShowVideoInfo; - BOOL m_bBigShow; - - BOOL m_bBackground; -public: - afx_msg void OnPaint(); -}; - - diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AgoraAudInputManager.cpp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AgoraAudInputManager.cpp deleted file mode 100644 index b5073e5e..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AgoraAudInputManager.cpp +++ /dev/null @@ -1,165 +0,0 @@ -#include "stdafx.h" -#include "AgoraAudInputManager.h" - - -CAgoraAudInputManager::CAgoraAudInputManager() - : m_ptrDeviceManager(NULL) - , m_lpCollection(NULL) - , m_bTestingOn(FALSE) -{ -} - - -CAgoraAudInputManager::~CAgoraAudInputManager() -{ - Close(); -} - -BOOL CAgoraAudInputManager::Create(IRtcEngine *lpRtcEngine) -{ - m_ptrDeviceManager = new AAudioDeviceManager(lpRtcEngine); - if (m_ptrDeviceManager == NULL || m_ptrDeviceManager->get() == NULL) - return FALSE; - - m_lpCollection = (*m_ptrDeviceManager)->enumerateRecordingDevices(); - if (m_lpCollection == NULL) { - delete m_ptrDeviceManager; - m_ptrDeviceManager = NULL; - } - - - return m_lpCollection != NULL ? TRUE : FALSE; -} - -void CAgoraAudInputManager::Close() -{ - if (m_lpCollection != NULL){ - m_lpCollection->release(); - m_lpCollection = NULL; - } - - if (m_ptrDeviceManager != NULL) { - delete m_ptrDeviceManager; - m_ptrDeviceManager = NULL; - } -} - -UINT CAgoraAudInputManager::GetVolume() -{ - int nVol = 0; - - if (m_ptrDeviceManager == NULL || m_ptrDeviceManager->get() == NULL) - return 0; - - (*m_ptrDeviceManager)->getRecordingDeviceVolume(&nVol); - - return (UINT)nVol; -} - -BOOL CAgoraAudInputManager::SetVolume(UINT nVol) -{ - if (m_ptrDeviceManager == NULL || m_ptrDeviceManager->get() == NULL) - return FALSE; - - int nRet = (*m_ptrDeviceManager)->setRecordingDeviceVolume((int)nVol); - - return nRet == 0 ? TRUE : FALSE; -} - -UINT CAgoraAudInputManager::GetDeviceCount() -{ - if (m_lpCollection != NULL) - return (UINT)m_lpCollection->getCount(); - - return 0; -} - -BOOL CAgoraAudInputManager::GetDevice(UINT nIndex, CString &rDeviceName, CString &rDeviceID) -{ - CHAR szDeviceName[MAX_DEVICE_ID_LENGTH]; - CHAR szDeviceID[MAX_DEVICE_ID_LENGTH]; - - ASSERT(nIndex < GetDeviceCount()); - - if (nIndex >= GetDeviceCount()) - return FALSE; - - if (m_lpCollection == NULL) - return FALSE; - - int nRet = m_lpCollection->getDevice(nIndex, szDeviceName, szDeviceID); - if (nRet != 0) - return FALSE; - -#ifdef UNICODE - ::MultiByteToWideChar(CP_UTF8, 0, szDeviceName, -1, rDeviceName.GetBuffer(MAX_DEVICE_ID_LENGTH), MAX_DEVICE_ID_LENGTH); - ::MultiByteToWideChar(CP_UTF8, 0, szDeviceID, -1, rDeviceID.GetBuffer(MAX_DEVICE_ID_LENGTH), MAX_DEVICE_ID_LENGTH); - - rDeviceName.ReleaseBuffer(); - rDeviceID.ReleaseBuffer(); -#else - strDeviceName = szDeviceName; - strDeviceID = szDeviceID; -#endif - - return TRUE; -} - -CString CAgoraAudInputManager::GetCurDeviceID() -{ - CString str; - CHAR szDeviceID[MAX_DEVICE_ID_LENGTH]; - - if (m_ptrDeviceManager == NULL || m_ptrDeviceManager->get() == NULL) - return str; - - (*m_ptrDeviceManager)->getRecordingDevice(szDeviceID); - -#ifdef UNICODE - ::MultiByteToWideChar(CP_UTF8, 0, szDeviceID, -1, str.GetBuffer(MAX_DEVICE_ID_LENGTH), MAX_DEVICE_ID_LENGTH); - str.ReleaseBuffer(); -#else - strDeviceName = szDeviceID; -#endif - - return str; -} - -BOOL CAgoraAudInputManager::SetCurDevice(LPCTSTR lpDeviceID) -{ - if (m_ptrDeviceManager == NULL || m_ptrDeviceManager->get() == NULL) - return FALSE; - -#ifdef UNICODE - CHAR szDeviceID[128]; - ::WideCharToMultiByte(CP_ACP, 0, lpDeviceID, -1, szDeviceID, 128, NULL, NULL); - int nRet = (*m_ptrDeviceManager)->setRecordingDevice(szDeviceID); -#else - int nRet = (*m_ptrDeviceManager)->setRecordingDevice(lpDeviceID); -#endif - - return nRet == 0 ? TRUE : FALSE; -} - -void CAgoraAudInputManager::TestAudInputDevice(HWND hMsgWnd, BOOL bTestOn) -{ - if (m_ptrDeviceManager == NULL || m_ptrDeviceManager->get() == NULL) - return; - - if (bTestOn && !m_bTestingOn) { - m_hOldMsgWnd = CAgoraObject::GetAgoraObject()->GetMsgHandlerWnd(); - CAgoraObject::GetAgoraObject()->SetMsgHandlerWnd(hMsgWnd); - - IRtcEngine *lpRtcEngine = CAgoraObject::GetEngine(); - RtcEngineParameters rep(*lpRtcEngine); - rep.enableAudioVolumeIndication(1000, 10,true); - (*m_ptrDeviceManager)->startRecordingDeviceTest(1000); - } - else if (!bTestOn && m_bTestingOn){ - CAgoraObject::GetAgoraObject()->SetMsgHandlerWnd(m_hOldMsgWnd); - (*m_ptrDeviceManager)->stopRecordingDeviceTest(); - } - - m_bTestingOn = bTestOn; - -} \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AgoraAudInputManager.h b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AgoraAudInputManager.h deleted file mode 100644 index 8d58061c..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AgoraAudInputManager.h +++ /dev/null @@ -1,29 +0,0 @@ -#pragma once -class CAgoraAudInputManager -{ -public: - CAgoraAudInputManager(); - ~CAgoraAudInputManager(); - - BOOL Create(IRtcEngine *lpRtcEngine); - void Close(); - - UINT GetVolume(); - BOOL SetVolume(UINT nVol); - UINT GetDeviceCount(); - - CString GetCurDeviceID(); - BOOL SetCurDevice(LPCTSTR lpDeviceID); - - BOOL GetDevice(UINT nIndex, CString &rDeviceName, CString &rDeviceID); - - void TestAudInputDevice(HWND hMsgWnd, BOOL bTestOn); - - BOOL IsTesting() { return m_bTestingOn; }; -private: - BOOL m_bTestingOn; - HWND m_hOldMsgWnd; - AAudioDeviceManager *m_ptrDeviceManager; - IAudioDeviceCollection *m_lpCollection; -}; - diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AgoraCameraManager.cpp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AgoraCameraManager.cpp deleted file mode 100644 index af03dd0f..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AgoraCameraManager.cpp +++ /dev/null @@ -1,134 +0,0 @@ -#include "stdafx.h" -#include "AgoraCameraManager.h" - - -CAgoraCameraManager::CAgoraCameraManager() - : m_ptrDeviceManager(NULL) - , m_lpCollection(NULL) -{ -} - - -CAgoraCameraManager::~CAgoraCameraManager() -{ - Close(); -} - -BOOL CAgoraCameraManager::Create(IRtcEngine *lpRtcEngine) -{ -// lpRtcEngine->enableVideo(); - - m_ptrDeviceManager = new AVideoDeviceManager(lpRtcEngine); - if (m_ptrDeviceManager == NULL || m_ptrDeviceManager->get() == NULL) - return FALSE; - - m_lpCollection = (*m_ptrDeviceManager)->enumerateVideoDevices(); - if (m_lpCollection == NULL) { - delete m_ptrDeviceManager; - m_ptrDeviceManager = NULL; - } - - return m_lpCollection != NULL ? TRUE : FALSE; -} - -void CAgoraCameraManager::Close() -{ - if (m_lpCollection != NULL){ - m_lpCollection->release(); - m_lpCollection = NULL; - } - - if (m_ptrDeviceManager != NULL) { - delete m_ptrDeviceManager; - m_ptrDeviceManager = NULL; - } -} - -UINT CAgoraCameraManager::GetDeviceCount() -{ - if (m_lpCollection == NULL) - return 0; - - return (UINT)m_lpCollection->getCount(); -} - -CString CAgoraCameraManager::GetCurDeviceID() -{ - CString str; - CHAR szDeviceID[MAX_DEVICE_ID_LENGTH]; - - if (m_ptrDeviceManager == NULL || m_ptrDeviceManager->get() == NULL) - return str; - - memset(szDeviceID, 0x00, MAX_DEVICE_ID_LENGTH); - if (m_ptrDeviceManager != NULL && m_ptrDeviceManager->get() != NULL) - (*m_ptrDeviceManager)->getDevice(szDeviceID); - -#ifdef UNICODE - ::MultiByteToWideChar(CP_UTF8, 0, szDeviceID, -1, str.GetBuffer(MAX_DEVICE_ID_LENGTH), MAX_DEVICE_ID_LENGTH); - str.ReleaseBuffer(); -#else - strDeviceName = szDeviceID; -#endif - - return str; -} - -BOOL CAgoraCameraManager::GetDevice(UINT nIndex, CString &rDeviceName, CString &rDeviceID) -{ - CHAR szDeviceName[MAX_DEVICE_ID_LENGTH]; - CHAR szDeviceID[MAX_DEVICE_ID_LENGTH]; - - ASSERT(nIndex < GetDeviceCount()); - if (nIndex >= GetDeviceCount()) - return FALSE; - - if(m_lpCollection == NULL) - return FALSE; - - int nRet = m_lpCollection->getDevice(nIndex, szDeviceName, szDeviceID); - if (nRet != 0) - return FALSE; - -#ifdef UNICODE - ::MultiByteToWideChar(CP_UTF8, 0, szDeviceName, -1, rDeviceName.GetBuffer(MAX_DEVICE_ID_LENGTH), MAX_DEVICE_ID_LENGTH); - ::MultiByteToWideChar(CP_UTF8, 0, szDeviceID, -1, rDeviceID.GetBuffer(MAX_DEVICE_ID_LENGTH), MAX_DEVICE_ID_LENGTH); - - rDeviceName.ReleaseBuffer(); - rDeviceID.ReleaseBuffer(); -#else - strDeviceName = szDeviceName; - strDeviceID = szDeviceID; -#endif - - return TRUE; -} - -BOOL CAgoraCameraManager::SetCurDevice(LPCTSTR lpDeviceID) -{ - if (m_ptrDeviceManager == NULL || *m_ptrDeviceManager == NULL) - return FALSE; - -#ifdef UNICODE - CHAR szDeviceID[128]; - ::WideCharToMultiByte(CP_UTF8, 0, lpDeviceID, -1, szDeviceID, 128, NULL, NULL); - int nRet = (*m_ptrDeviceManager)->setDevice(szDeviceID); -#else - int nRet = (*m_ptrDeviceManager)->setDevice(lpDeviceID); -#endif - - return nRet == 0 ? TRUE : FALSE; -} - -void CAgoraCameraManager::TestCameraDevice(HWND hVideoWnd, BOOL bTestOn) -{ - if (bTestOn && !m_bTestingOn) { - ASSERT(hVideoWnd != NULL); - CAgoraObject::GetAgoraObject()->LocalVideoPreview(hVideoWnd, TRUE); - } - else if(!bTestOn && m_bTestingOn){ - CAgoraObject::GetAgoraObject()->LocalVideoPreview(NULL, FALSE); - } - - m_bTestingOn = bTestOn; -} \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AgoraCameraManager.h b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AgoraCameraManager.h deleted file mode 100644 index 45c4c71a..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AgoraCameraManager.h +++ /dev/null @@ -1,26 +0,0 @@ -#pragma once -class CAgoraCameraManager -{ -public: - CAgoraCameraManager(); - ~CAgoraCameraManager(); - - BOOL Create(IRtcEngine *lpRtcEngine); - void Close(); - - UINT GetDeviceCount(); - - CString GetCurDeviceID(); - BOOL SetCurDevice(LPCTSTR lpDeviceID); - - BOOL GetDevice(UINT nIndex, CString &rDeviceName, CString &rDeviceID); - void TestCameraDevice(HWND hVideoWnd, BOOL bTestOn = TRUE); - - BOOL IsTesting() { return m_bTestingOn; }; - -private: - AVideoDeviceManager *m_ptrDeviceManager; - IVideoDeviceCollection *m_lpCollection; - BOOL m_bTestingOn; -}; - diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AgoraObject.cpp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AgoraObject.cpp deleted file mode 100644 index d87f000a..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AgoraObject.cpp +++ /dev/null @@ -1,621 +0,0 @@ -#include "StdAfx.h" -#include "AgoraObject.h" -#include "AGResourceVisitor.h" - -#include - - -CAgoraObject *CAgoraObject::m_lpAgoraObject = NULL; -IRtcEngine *CAgoraObject::m_lpAgoraEngine = NULL; -CAGEngineEventHandler CAgoraObject::m_EngineEventHandler; -CString CAgoraObject::m_strVendorKey; - -CAgoraObject::CAgoraObject(void) - : m_dwEngineFlag(0) - , m_bVideoEnable(FALSE) - , m_bLocalAudioMuted(FALSE) - , m_bScreenCapture(FALSE) - , m_bEchoTest(FALSE) - , m_nSelfUID(0) -{ - m_strChannelName.Empty(); - m_bLocalVideoMuted = FALSE; -} - -CAgoraObject::~CAgoraObject(void) -{ -} - -CString CAgoraObject::LoadAppID() -{ - TCHAR szFilePath[MAX_PATH]; - CString strAppID(APP_ID); - - ::GetModuleFileName(NULL, szFilePath, MAX_PATH); - LPTSTR lpLastSlash = _tcsrchr(szFilePath, _T('\\')); - - if (lpLastSlash == NULL) - return strAppID; - - SIZE_T nNameLen = MAX_PATH - (lpLastSlash - szFilePath + 1); - _tcscpy_s(lpLastSlash + 1, nNameLen, _T("AppID.ini")); - - if (::GetFileAttributes(szFilePath) == INVALID_FILE_ATTRIBUTES) - return strAppID; - - CString strResolution; - - ::GetPrivateProfileString(_T("AppID"), _T("AppID"), NULL, strAppID.GetBuffer(MAX_PATH), MAX_PATH, szFilePath); - - strAppID.ReleaseBuffer(); - - return strAppID; -} - - -CString CAgoraObject::GetSDKVersion() -{ - int nBuildNumber = 0; - const char *lpszEngineVer = getAgoraRtcEngineVersion(&nBuildNumber); - - CString strEngineVer; - -#ifdef UNICODE - ::MultiByteToWideChar(CP_ACP, MB_PRECOMPOSED, lpszEngineVer, -1, strEngineVer.GetBuffer(256), 256); - strEngineVer.ReleaseBuffer(); -#endif - - return strEngineVer; -} - -CString CAgoraObject::GetSDKVersionEx() -{ - int nBuildNumber = 0; - const char *lpszEngineVer = getAgoraRtcEngineVersion(&nBuildNumber); - - CString strEngineVer; - CString strVerEx; - SYSTEMTIME sysTime; - -#ifdef UNICODE - ::MultiByteToWideChar(CP_ACP, MB_PRECOMPOSED, lpszEngineVer, -1, strEngineVer.GetBuffer(256), 256); - strEngineVer.ReleaseBuffer(); -#else - strEngineVer = lpszEngineVer; -#endif - - ::GetLocalTime(&sysTime); - strVerEx.Format(_T("V%s, Build%d, %d/%d/%d, V%s"), strEngineVer, nBuildNumber, sysTime.wYear, sysTime.wMonth, sysTime.wDay, strEngineVer); - - return strVerEx; -} - -IRtcEngine *CAgoraObject::GetEngine() -{ - if(m_lpAgoraEngine == NULL) - m_lpAgoraEngine = (IRtcEngine *)createAgoraRtcEngine(); - - return m_lpAgoraEngine; -} - -CAgoraObject *CAgoraObject::GetAgoraObject(LPCTSTR lpVendorKey) -{ - if(m_lpAgoraObject == NULL) - m_lpAgoraObject = new CAgoraObject(); - - if(m_lpAgoraEngine == NULL) - m_lpAgoraEngine = (IRtcEngine *)createAgoraRtcEngine(); - - // VendorKeyΪֱӷض - if (lpVendorKey == NULL) - return m_lpAgoraObject; - - RtcEngineContext ctx; - - ctx.eventHandler = &m_EngineEventHandler; - -#ifdef UNICODE - char szVendorKey[128]; - - ::WideCharToMultiByte(CP_ACP, 0, lpVendorKey, -1, szVendorKey, 128, NULL, NULL); - ctx.appId = szVendorKey; -#else - ctx.appId = lpVendorKey; -#endif - - m_lpAgoraEngine->initialize(ctx); - if (lpVendorKey != NULL) - m_strVendorKey = lpVendorKey; - - return m_lpAgoraObject; -} - -void CAgoraObject::CloseAgoraObject() -{ - if(m_lpAgoraEngine != NULL) - m_lpAgoraEngine->release(); - - if(m_lpAgoraObject != NULL) - delete m_lpAgoraObject; - - m_lpAgoraEngine = NULL; - m_lpAgoraObject = NULL; -} - -void CAgoraObject::SetMsgHandlerWnd(HWND hWnd) -{ - m_EngineEventHandler.SetMsgReceiver(hWnd); -} - -HWND CAgoraObject::GetMsgHandlerWnd() -{ - return m_EngineEventHandler.GetMsgReceiver(); -} - - -void CAgoraObject::SetNetworkTestFlag(BOOL bEnable) -{ - if(bEnable) - m_dwEngineFlag |= AG_ENGFLAG_ENNETTEST; - else - m_dwEngineFlag &= (~AG_ENGFLAG_ENNETTEST); -} - -BOOL CAgoraObject::GetNetworkTestFlag() -{ - return (m_dwEngineFlag & AG_ENGFLAG_ENNETTEST) != 0; -} - -void CAgoraObject::SetEchoTestFlag(BOOL bEnable) -{ - if(bEnable) - m_dwEngineFlag |= AG_ENGFLAG_ECHOTEST; - else - m_dwEngineFlag &= (~AG_ENGFLAG_ECHOTEST); -} - -BOOL CAgoraObject::GetEchoTestFlag() -{ - return (m_dwEngineFlag & AG_ENGFLAG_ECHOTEST) != 0; -} - -void CAgoraObject::SetSpeakerphoneTestFlag(BOOL bEnable) -{ - if(bEnable) - m_dwEngineFlag |= AG_ENGFLAG_SPKPHTEST; - else - m_dwEngineFlag &= (~AG_ENGFLAG_SPKPHTEST); -} - -BOOL CAgoraObject::GetSpeakerphoneTestFlag() -{ - return (m_dwEngineFlag & AG_ENGFLAG_SPKPHTEST) != 0; -} - -void CAgoraObject::SetMicrophoneTestFlag(BOOL bEnable) -{ - if(bEnable) - m_dwEngineFlag |= AG_ENGFLAG_MICPHTEST; - else - m_dwEngineFlag &= (~AG_ENGFLAG_MICPHTEST); -} - -BOOL CAgoraObject::GetMicrophoneTestFlag() -{ - return (m_dwEngineFlag & AG_ENGFLAG_MICPHTEST) != 0; -} - - -void CAgoraObject::SetVideoTestFlag(BOOL bEnable) -{ - if (bEnable) - m_dwEngineFlag |= AG_ENGFLAG_VIDEOTEST; - else - m_dwEngineFlag &= (~AG_ENGFLAG_VIDEOTEST); -} - -BOOL CAgoraObject::GetVideoTestFlag() -{ - return (m_dwEngineFlag & AG_ENGFLAG_VIDEOTEST) != 0; -} - -BOOL CAgoraObject::SetLogFilePath(LPCTSTR lpLogPath) -{ - ASSERT(m_lpAgoraEngine != NULL); - - CHAR szLogPathA[MAX_PATH]; - CHAR szLogPathTrans[MAX_PATH]; - - int ret = 0; - RtcEngineParameters rep(*m_lpAgoraEngine); - - if (::GetFileAttributes(lpLogPath) == INVALID_FILE_ATTRIBUTES) { - ::GetModuleFileNameA(NULL, szLogPathA, MAX_PATH); - LPSTR lpLastSlash = strrchr(szLogPathA, '\\')+1; - strcpy_s(lpLastSlash, 64, "AgoraSDK.log"); - } - else { -#ifdef UNICODE - ::WideCharToMultiByte(CP_UTF8, 0, lpLogPath, -1, szLogPathA, MAX_PATH, NULL, NULL); -#else - ::MultiByteToWideChar(CP_UTF8, 0, lpLogPath, -1, (WCHAR *)szLogPathA, MAX_PATH, NULL, NULL); -#endif - } - - CAGResourceVisitor::TransWinPathA(szLogPathA, szLogPathTrans, MAX_PATH); - - ret = rep.setLogFile(szLogPathTrans); - - return ret == 0 ? TRUE : FALSE; -} - -BOOL CAgoraObject::JoinChannel(LPCTSTR lpChannelName, UINT nUID, LPCSTR lpChannelToken) -{ - int nRet = 0; - -// m_lpAgoraEngine->setVideoProfile(VIDEO_PROFILE_720P); -#ifdef UNICODE - CHAR szChannelName[128]; - - ::WideCharToMultiByte(CP_ACP, 0, lpChannelName, -1, szChannelName, 128, NULL, NULL); - nRet = m_lpAgoraEngine->joinChannel(lpChannelToken, szChannelName, NULL, nUID); -#else - nRet = m_lpAgoraEngine->joinChannel(lpChannelToken, lpChannelName, NULL, nUID); -#endif - - if (nRet == 0) - m_strChannelName = lpChannelName; - - return nRet == 0 ? TRUE : FALSE; -} - -BOOL CAgoraObject::LeaveCahnnel() -{ - m_lpAgoraEngine->stopPreview(); - int nRet = m_lpAgoraEngine->leaveChannel(); - - return nRet == 0 ? TRUE : FALSE; -} - -CString CAgoraObject::GetChanelName() -{ - return m_strChannelName; -} - -CString CAgoraObject::GetCallID() -{ - agora::util::AString uid; - CString strUID; - - m_lpAgoraEngine->getCallId(uid); - -#ifdef UNICODE - ::MultiByteToWideChar(CP_ACP, 0, uid->c_str(), -1, strUID.GetBuffer(128), 128); - strUID.ReleaseBuffer(); -#else - strUID = uid->c_str(); -#endif - - return strUID; -} - -BOOL CAgoraObject::EnableVideo(BOOL bEnable) -{ - int nRet = 0; - - if (bEnable) - nRet = m_lpAgoraEngine->enableVideo(); - else - nRet = m_lpAgoraEngine->disableVideo(); - - if (nRet == 0) - m_bVideoEnable = bEnable; - - return nRet == 0 ? TRUE : FALSE; -} - -BOOL CAgoraObject::IsVideoEnabled() -{ - return m_bVideoEnable; -} - -BOOL CAgoraObject::EnableScreenCapture(HWND hWnd, int nCapFPS, LPCRECT lpCapRect, BOOL bEnable, int nBitrate) -{ - ASSERT(m_lpAgoraEngine != NULL); - - int ret = 0; - RtcEngineParameters rep(*m_lpAgoraEngine); - - agora::rtc::Rectangle rcCap; - ScreenCaptureParameters capParam; - capParam.bitrate = nBitrate; - capParam.frameRate = nCapFPS; - - if (bEnable) { - if (lpCapRect == NULL){ - RECT rc; - if (hWnd){ - GetWindowRect(hWnd, &rc); - capParam.dimensions.width = rc.right - rc.left; - capParam.dimensions.height = rc.bottom - rc.top; - ret = m_lpAgoraEngine->startScreenCaptureByWindowId(hWnd, rcCap, capParam); - } - else{ - GetWindowRect(GetDesktopWindow(), &rc); - agora::rtc::Rectangle screenRegion = { rc.left, rc.right, rc.right - rc.left, rc.bottom - rc.top }; - capParam.dimensions.width = rc.right - rc.left; - capParam.dimensions.height = rc.bottom - rc.top; - ret = m_lpAgoraEngine->startScreenCaptureByScreenRect(screenRegion, rcCap, capParam); - } - //startScreenCapture(hWnd, nCapFPS, NULL, nBitrate); - } - else { - capParam.dimensions.width = lpCapRect->right - lpCapRect->left; - capParam.dimensions.height = lpCapRect->bottom - lpCapRect->top; - - rcCap.x = lpCapRect->left; - rcCap.y = lpCapRect->top; - rcCap.width = lpCapRect->right - lpCapRect->left; - rcCap.height = lpCapRect->bottom - lpCapRect->top; - - if (hWnd) - ret = m_lpAgoraEngine->startScreenCaptureByWindowId(hWnd, rcCap, capParam); - else{ - - agora::rtc::Rectangle screenRegion = rcCap; - ret = m_lpAgoraEngine->startScreenCaptureByScreenRect(screenRegion, rcCap, capParam); - } - } - } - else - ret = m_lpAgoraEngine->stopScreenCapture(); - - if (ret == 0) - m_bScreenCapture = bEnable; - - return ret == 0 ? TRUE : FALSE; -} - -BOOL CAgoraObject::IsScreenCaptureEnabled() -{ - return m_bScreenCapture; -} - -BOOL CAgoraObject::MuteLocalAudio(BOOL bMuted) -{ - ASSERT(m_lpAgoraEngine != NULL); - - RtcEngineParameters rep(*m_lpAgoraEngine); - - int ret = rep.muteLocalAudioStream((bool)bMuted); - if (ret == 0) - m_bLocalAudioMuted = bMuted; - - return ret == 0 ? TRUE : FALSE; -} - -BOOL CAgoraObject::IsLocalAudioMuted() -{ - return m_bLocalAudioMuted; -} - - -BOOL CAgoraObject::MuteLocalVideo(BOOL bMuted) -{ - ASSERT(m_lpAgoraEngine != NULL); - - RtcEngineParameters rep(*m_lpAgoraEngine); - - int ret = rep.muteLocalVideoStream((bool)bMuted); - if (ret == 0) - m_bLocalVideoMuted = bMuted; - - return ret == 0 ? TRUE : FALSE; -} - -BOOL CAgoraObject::IsLocalVideoMuted() -{ - return m_bLocalVideoMuted; -} - - -BOOL CAgoraObject::EnableAudioRecording(BOOL bEnable, LPCTSTR lpFilePath) -{ - int ret = 0; - - RtcEngineParameters rep(*m_lpAgoraEngine); - - if (bEnable) { -#ifdef UNICODE - CHAR szFilePath[MAX_PATH]; - ::WideCharToMultiByte(CP_ACP, 0, lpFilePath, -1, szFilePath, MAX_PATH, NULL, NULL); - ret = rep.startAudioRecording(szFilePath, AUDIO_RECORDING_QUALITY_HIGH); -#else - ret = rep.startAudioRecording(lpFilePath); -#endif - } - else - ret = rep.stopAudioRecording(); - - return ret == 0 ? TRUE : FALSE; -} - -BOOL CAgoraObject::EnableNetworkTest(BOOL bEnable) -{ - int ret = 0; - - - if (bEnable) - ret = m_lpAgoraEngine->enableLastmileTest(); - else - ret = m_lpAgoraEngine->disableLastmileTest(); - - return ret == 0 ? TRUE : FALSE; -} - -BOOL CAgoraObject::EnableEchoTest(BOOL bEnable) -{ - int ret = 0; - - if (bEnable) - ret = m_lpAgoraEngine->startEchoTest(); - else - ret = m_lpAgoraEngine->stopEchoTest(); - - if (ret == 0) - m_bEchoTest = bEnable; - - return ret == 0 ? TRUE : FALSE; -} - -BOOL CAgoraObject::LocalVideoPreview(HWND hVideoWnd, BOOL bPreviewOn) -{ - int nRet = 0; - - if (bPreviewOn) { - VideoCanvas vc; - - vc.uid = 0; - vc.view = hVideoWnd; - vc.renderMode = RENDER_MODE_TYPE::RENDER_MODE_HIDDEN; - - m_lpAgoraEngine->setupLocalVideo(vc); - nRet = m_lpAgoraEngine->startPreview(); - } - else - nRet = m_lpAgoraEngine->stopPreview(); - - return nRet == 0 ? TRUE : FALSE; -} - -BOOL CAgoraObject::SetLogFilter(UINT logFilterType, LPCTSTR lpLogPath) -{ - int nRet = 0; - RtcEngineParameters rep(*m_lpAgoraEngine); - - nRet = rep.setLogFilter(logFilterType); - -#ifdef UNICODE - CHAR szFilePath[MAX_PATH]; - ::WideCharToMultiByte(CP_ACP, 0, lpLogPath, -1, szFilePath, MAX_PATH, NULL, NULL); - nRet |= rep.setLogFile(szFilePath); -#else - nRet |= rep.setLogFile(lpLogPath); -#endif - - return nRet == 0 ? TRUE : FALSE; -} - -BOOL CAgoraObject::SetEncryptionSecret(LPCTSTR lpKey, int nEncryptType) -{ - CHAR szUTF8[MAX_PATH]; - -#ifdef UNICODE - ::WideCharToMultiByte(CP_UTF8, 0, lpKey, -1, szUTF8, MAX_PATH, NULL, NULL); -#else - WCHAR szAnsi[MAX_PATH]; - ::MultiByteToWideChar(CP_ACP, 0, lpKey, -1, szAnsi, MAX_PATH); - ::WideCharToMultiByte(CP_UTF8, 0, szAnsi, -1, szUTF8, MAX_PATH, NULL, NULL); -#endif - switch (nEncryptType) - { - case 0: - m_lpAgoraEngine->setEncryptionMode("aes-128-xts"); - break; - case 1: - m_lpAgoraEngine->setEncryptionMode("aes-256-xts"); - break; - default: - m_lpAgoraEngine->setEncryptionMode("aes-128-xts"); - break; - } - int nRet = m_lpAgoraEngine->setEncryptionSecret(szUTF8); - - return nRet == 0 ? TRUE : FALSE; -} - -BOOL CAgoraObject::EnableLocalRender(BOOL bEnable) -{ - int nRet = 0; - -/* if (bEnable) - nRet = m_lpAgoraEngine->setParameters("{\"che.video.local.render\":true}"); - else - nRet = m_lpAgoraEngine->setParameters("{\"che.video.local.render\":false}"); -*/ - return nRet == 0 ? TRUE : FALSE; -} - -int CAgoraObject::CreateMessageStream() -{ - int nDataStream = 0; - m_lpAgoraEngine->createDataStream(&nDataStream, true, true); - - return nDataStream; -} - -BOOL CAgoraObject::SendChatMessage(int nStreamID, LPCTSTR lpChatMessage) -{ - _ASSERT(nStreamID != 0); - int nMessageLen = _tcslen(lpChatMessage); - _ASSERT(nMessageLen < 128); - - CHAR szUTF8[256]; - -#ifdef UNICODE - int nUTF8Len = ::WideCharToMultiByte(CP_UTF8, 0, lpChatMessage, nMessageLen, szUTF8, 256, NULL, NULL); -#else - int nUTF8Len = ::MultiByteToWideChar(CP_UTF8, lpChatMessage, nMessageLen, szUTF8, 256); -#endif - - int nRet = m_lpAgoraEngine->sendStreamMessage(nStreamID, szUTF8, nUTF8Len); - - return nRet == 0 ? TRUE : FALSE; -} - - -BOOL CAgoraObject::EnableWhiteboardVer(BOOL bEnable) -{ - // HKEY_LOCAL_MACHINE\SOFTWARE\Wow6432Node\Microsoft\Internet Explorer\MAIN\FeatureControl\FEATURE_BROWSER_EMULATION - HKEY hKey = NULL; - - LSTATUS lStatus = ::RegCreateKeyEx(HKEY_CURRENT_USER, _T("SOFTWARE\\Wow6432Node\\Microsoft\\Internet Explorer\\MAIN\\FeatureControl\\FEATURE_BROWSER_EMULATION"), 0, REG_OPTION_NON_VOLATILE - , REG_OPTION_NON_VOLATILE, KEY_WRITE, NULL, &hKey, NULL); - - if (lStatus != ERROR_SUCCESS) - return FALSE; - - DWORD dwIEVer = 11001; - - if (bEnable) - lStatus = ::RegSetValueEx(hKey, _T("AgoraVideoCall.exe"), 0, REG_DWORD, (const BYTE*)&dwIEVer, sizeof(DWORD)); - else - lStatus = ::RegDeleteKeyValue(hKey, NULL, _T("AgoraVideoCall.exe")); - - ::RegCloseKey(hKey); - - return lStatus == ERROR_SUCCESS ? TRUE : FALSE; -} - -BOOL CAgoraObject::EnableWhiteboardFeq(BOOL bEnable) -{ - // HKEY_LOCAL_MACHINE\SOFTWARE\Wow6432Node\Microsoft\Internet Explorer\MAIN\FeatureControl\FEATURE_BROWSER_EMULATION - HKEY hKey = NULL; - - LSTATUS lStatus = ::RegCreateKeyEx(HKEY_CURRENT_USER, _T("SOFTWARE\\Wow6432Node\\Microsoft\\Internet Explorer\\MAIN\\FeatureControl\\FEATURE_MANAGE_SCRIPT_CIRCULAR_REFS"), 0, REG_OPTION_NON_VOLATILE - , REG_OPTION_NON_VOLATILE, KEY_WRITE, NULL, &hKey, NULL); - - if (lStatus != ERROR_SUCCESS) - return FALSE; - - DWORD dwValue = 1; - - if (bEnable) - lStatus = ::RegSetValueEx(hKey, _T("AgoraVideoCall.exe"), 0, REG_DWORD, (const BYTE*)&dwValue, sizeof(DWORD)); - else - lStatus = ::RegDeleteKeyValue(hKey, NULL, _T("AgoraVideoCall.exe")); - - ::RegCloseKey(hKey); - - return lStatus == ERROR_SUCCESS ? TRUE : FALSE; -} \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AgoraObject.h b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AgoraObject.h deleted file mode 100644 index 0ef9c0e6..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AgoraObject.h +++ /dev/null @@ -1,137 +0,0 @@ -#pragma once - -#include -#include "AGEngineEventHandler.h" - -#define AVC_VER _T("V1.12.0, Build234, 08/14/2017, SDK1.12 .0") - -using namespace agora::rtc; - -// ������λ -#define AG_ENGFLAG_ENNETTEST 0x00000001 -#define AG_ENGFLAG_ECHOTEST 0x00000002 -#define AG_ENGFLAG_SPKPHTEST 0x00000004 -#define AG_ENGFLAG_MICPHTEST 0x00000008 -#define AG_ENGFLAG_VIDEOTEST 0x00000010 - - -#define AG_CODEC_E264 0x00000000 -#define AG_CODEC_EVP 0x00000001 -#define AG_CODEC_VP8 0x00000002 - -/* NOTE: - PLEASE KEEP THIS App ID IN SAFE PLACE - Get your own App ID at https://dashboard.agora.io/ - After you entered the App ID, remove <##> outside of Your App ID - APP_ID _T("") - Obtain a temp Access Token at https://dashboard.agora.io - You will need to deploy your own token server for production release - Leave this value empty if Security keys/Token is not enabled for your project - APP_TOKEN "" -*/ -#define APP_ID _T("") -#define APP_TOKEN "" - -class CAgoraObject -{ -public: - ~CAgoraObject(void); - - static CString LoadAppID(); - - void SetNetworkTestFlag(BOOL bEnable); - BOOL GetNetworkTestFlag(); - - void SetEchoTestFlag(BOOL bEnable); - BOOL GetEchoTestFlag(); - - void SetSpeakerphoneTestFlag(BOOL bEnable); - BOOL GetSpeakerphoneTestFlag(); - - void SetMicrophoneTestFlag(BOOL bEnable); - BOOL GetMicrophoneTestFlag(); - - void SetVideoTestFlag(BOOL bEnable); - BOOL GetVideoTestFlag(); - - void SetMsgHandlerWnd(HWND hWnd); - HWND GetMsgHandlerWnd(); - - BOOL SetLogFilePath(LPCTSTR lpLogPath = NULL); - - BOOL JoinChannel(LPCTSTR lpChannelName, UINT nUID = 0,LPCSTR lpChannelToken = NULL); - BOOL LeaveCahnnel(); - CString GetChanelName(); - CString GetCallID(); - CString GetVendorKey() { return m_strVendorKey; }; - - void SetSelfUID(UINT nUID) { m_nSelfUID = nUID; }; - UINT GetSelfUID() { return m_nSelfUID; }; - - BOOL EnableVideo(BOOL bEnable = TRUE); - BOOL IsVideoEnabled(); - - BOOL EnableScreenCapture(HWND hWnd, int nCapFPS = 15, LPCRECT lpCapRect = NULL, BOOL bEnable = TRUE, int nBitrate = 0); - BOOL IsScreenCaptureEnabled(); - - BOOL MuteLocalAudio(BOOL bMuted = TRUE); - BOOL IsLocalAudioMuted(); - - BOOL MuteLocalVideo(BOOL bMuted = TRUE); - BOOL IsLocalVideoMuted(); - - BOOL EnableAudioRecording(BOOL bEnable, LPCTSTR lpFilePath); - - BOOL EnableNetworkTest(BOOL bEnable); - - BOOL EnableEchoTest(BOOL bEnable = TRUE); - BOOL IsEchoTesting() { return m_bEchoTest; }; - - BOOL LocalVideoPreview(HWND hVideoWnd, BOOL bPreviewOn = TRUE); - - BOOL SetLogFilter(UINT logFilterType, LPCTSTR lpLogPath); - - BOOL SetEncryptionSecret(LPCTSTR lpKey, int nEncryptType = 0); - - BOOL EnableLocalRender(BOOL bEnable); - - int CreateMessageStream(); - BOOL SendChatMessage(int nStreamID, LPCTSTR lpChatMessage); - - static IRtcEngine *GetEngine(); - - static CString GetSDKVersion(); - static CString GetSDKVersionEx(); - - static BOOL EnableWhiteboardVer(BOOL bEnable); - static BOOL EnableWhiteboardFeq(BOOL bEnable); - - - -protected: - CAgoraObject(void); - -private: - DWORD m_dwEngineFlag; - static CAgoraObject *m_lpAgoraObject; - static IRtcEngine *m_lpAgoraEngine; - static CString m_strVendorKey; - - UINT m_nSelfUID; - CString m_strChannelName; - BOOL m_bVideoEnable; - - BOOL m_bLocalAudioMuted; - BOOL m_bLocalVideoMuted; - BOOL m_bEchoTest; - - BOOL m_bScreenCapture; - -// int m_nCodecType; - -public: - static CAgoraObject *GetAgoraObject(LPCTSTR lpVendorKey = NULL); - static void CloseAgoraObject(); - - static CAGEngineEventHandler m_EngineEventHandler; -}; diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AgoraPlayoutManager.cpp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AgoraPlayoutManager.cpp deleted file mode 100644 index 0cacc7f8..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AgoraPlayoutManager.cpp +++ /dev/null @@ -1,167 +0,0 @@ -#include "stdafx.h" -#include "AgoraPlayoutManager.h" -#include "AGResourceVisitor.h" - -CAgoraPlayoutManager::CAgoraPlayoutManager() - : m_ptrDeviceManager(NULL) - , m_lpCollection(NULL) - , m_bTestingOn(FALSE) -{ -} - - -CAgoraPlayoutManager::~CAgoraPlayoutManager() -{ - Close(); -} - -BOOL CAgoraPlayoutManager::Create(IRtcEngine *lpRtcEngine) -{ - m_ptrDeviceManager = new AAudioDeviceManager(lpRtcEngine); - if (m_ptrDeviceManager == NULL || m_ptrDeviceManager->get() == NULL) - return FALSE; - - m_lpCollection = (*m_ptrDeviceManager)->enumeratePlaybackDevices(); - if (m_lpCollection == NULL) { - delete m_ptrDeviceManager; - m_ptrDeviceManager = NULL; - } - - return m_lpCollection != NULL ? TRUE : FALSE; -} - -void CAgoraPlayoutManager::Close() -{ - if (m_lpCollection != NULL){ - m_lpCollection->release(); - m_lpCollection = NULL; - } - - if (m_ptrDeviceManager != NULL) { - delete m_ptrDeviceManager; - m_ptrDeviceManager = NULL; - } -} - -UINT CAgoraPlayoutManager::GetVolume() -{ - int nVol = 0; - - if (m_ptrDeviceManager == NULL || m_ptrDeviceManager->get() == NULL) - return 0; - - (*m_ptrDeviceManager)->getPlaybackDeviceVolume(&nVol); - - return (UINT)nVol; -} - -BOOL CAgoraPlayoutManager::SetVolume(UINT nVol) -{ - if (m_ptrDeviceManager == NULL || m_ptrDeviceManager->get() == NULL) - return 0; - - int nRet = (*m_ptrDeviceManager)->setPlaybackDeviceVolume((int)nVol); - - return nRet == 0 ? TRUE : FALSE; -} - -UINT CAgoraPlayoutManager::GetDeviceCount() -{ - if (m_lpCollection == NULL) - return 0; - - return (UINT)m_lpCollection->getCount(); -} - -BOOL CAgoraPlayoutManager::GetDevice(UINT nIndex, CString &rDeviceName, CString &rDeviceID) -{ - CHAR szDeviceName[MAX_DEVICE_ID_LENGTH]; - CHAR szDeviceID[MAX_DEVICE_ID_LENGTH]; - - ASSERT(nIndex < GetDeviceCount()); - if (nIndex >= GetDeviceCount()) - return FALSE; - - int nRet = m_lpCollection->getDevice(nIndex, szDeviceName, szDeviceID); - if (nRet != 0) - return FALSE; - -#ifdef UNICODE - ::MultiByteToWideChar(CP_UTF8, 0, szDeviceName, -1, rDeviceName.GetBuffer(MAX_DEVICE_ID_LENGTH), MAX_DEVICE_ID_LENGTH); - ::MultiByteToWideChar(CP_UTF8, 0, szDeviceID, -1, rDeviceID.GetBuffer(MAX_DEVICE_ID_LENGTH), MAX_DEVICE_ID_LENGTH); - - rDeviceName.ReleaseBuffer(); - rDeviceID.ReleaseBuffer(); -#else - strDeviceName = szDeviceName; - strDeviceID = szDeviceID; -#endif - - return TRUE; -} - -CString CAgoraPlayoutManager::GetCurDeviceID() -{ - CString str; - CHAR szDeviceID[MAX_DEVICE_ID_LENGTH]; - - if (m_ptrDeviceManager == NULL || m_ptrDeviceManager->get() == NULL) - return str; - - (*m_ptrDeviceManager)->getPlaybackDevice(szDeviceID); - -#ifdef UNICODE - ::MultiByteToWideChar(CP_UTF8, 0, szDeviceID, -1, str.GetBuffer(MAX_DEVICE_ID_LENGTH), MAX_DEVICE_ID_LENGTH); - str.ReleaseBuffer(); -#else - strDeviceName = szDeviceID; -#endif - - return str; -} - -BOOL CAgoraPlayoutManager::SetCurDevice(LPCTSTR lpDeviceID) -{ - if (m_ptrDeviceManager == NULL || m_ptrDeviceManager->get() == NULL) - return FALSE; - -#ifdef UNICODE - CHAR szDeviceID[128]; - ::WideCharToMultiByte(CP_ACP, 0, lpDeviceID, -1, szDeviceID, 128, NULL, NULL); - int nRet = (*m_ptrDeviceManager)->setPlaybackDevice(szDeviceID); -#else - int nRet = (*m_ptrDeviceManager)->setPlaybackDevice(lpDeviceID); -#endif - - return nRet == 0 ? TRUE : FALSE; -} - -void CAgoraPlayoutManager::TestPlaybackDevice(UINT nWavID, BOOL bTestOn) -{ - TCHAR szWavPath[MAX_PATH]; - - if (m_ptrDeviceManager == NULL || m_ptrDeviceManager->get() == NULL) - return; - - ::GetModuleFileName(NULL, szWavPath, MAX_PATH); - LPTSTR lpLastSlash = (LPTSTR)_tcsrchr(szWavPath, _T('\\')) + 1; - _tcscpy_s(lpLastSlash, 16, _T("test.wav")); - - if (bTestOn && !m_bTestingOn) { - CAGResourceVisitor::SaveResourceToFile(_T("WAVE"), nWavID, szWavPath); - -#ifdef UNICODE - CHAR szWavPathA[MAX_PATH]; - - ::WideCharToMultiByte(CP_ACP, 0, szWavPath, -1,szWavPathA , MAX_PATH, NULL, NULL); - (*m_ptrDeviceManager)->startPlaybackDeviceTest(szWavPathA); -#else - (*m_ptrDeviceManager)->startPlaybackDeviceTest(szWavPathA); -#endif - } - else if (!bTestOn && m_bTestingOn) - (*m_ptrDeviceManager)->stopPlaybackDeviceTest(); - - m_bTestingOn = bTestOn; - -} \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AgoraPlayoutManager.h b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AgoraPlayoutManager.h deleted file mode 100644 index fe446b75..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/AgoraPlayoutManager.h +++ /dev/null @@ -1,29 +0,0 @@ -#pragma once -class CAgoraPlayoutManager -{ -public: - CAgoraPlayoutManager(); - ~CAgoraPlayoutManager(); - - BOOL Create(IRtcEngine *lpRtcEngine); - void Close(); - - UINT GetVolume(); - BOOL SetVolume(UINT nVol); - UINT GetDeviceCount(); - - CString GetCurDeviceID(); - BOOL SetCurDevice(LPCTSTR lpDeviceID); - - BOOL GetDevice(UINT nIndex, CString &rDeviceName, CString &rDeviceID); - void TestPlaybackDevice(UINT nWavID, BOOL bTestOn = TRUE); - - BOOL IsTesting() { return m_bTestingOn; }; -private: - AAudioDeviceManager *m_ptrDeviceManager; - IAudioDeviceCollection *m_lpCollection; - -private: - BOOL m_bTestingOn; -}; - diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/ChatDlg.cpp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/ChatDlg.cpp deleted file mode 100644 index 99d9a260..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/ChatDlg.cpp +++ /dev/null @@ -1,129 +0,0 @@ -// ChatDlg.cpp : ʵļ -// - -#include "stdafx.h" -#include "OpenVideoCall.h" -#include "ChatDlg.h" -#include "afxdialogex.h" - - -// CChatDlg Ի - -IMPLEMENT_DYNAMIC(CChatDlg, CDialogEx) - -CChatDlg::CChatDlg(CWnd* pParent /*=NULL*/) - : CDialogEx(CChatDlg::IDD, pParent) -{ - -} - -CChatDlg::~CChatDlg() -{ -} - -void CChatDlg::DoDataExchange(CDataExchange* pDX) -{ - CDialogEx::DoDataExchange(pDX); - DDX_Control(pDX, IDC_EDCHAT_MESSAGE, m_edtChatBox); -} - - -BEGIN_MESSAGE_MAP(CChatDlg, CDialogEx) - ON_WM_SIZE() - ON_WM_PAINT() -END_MESSAGE_MAP() - - -// CChatDlg Ϣ - - -BOOL CChatDlg::OnInitDialog() -{ - CDialogEx::OnInitDialog(); - - // TODO: ڴӶijʼ - LONG lExStyle = ::GetWindowLong(GetSafeHwnd(), GWL_EXSTYLE); - ::SetWindowLong(GetSafeHwnd(), GWL_EXSTYLE, lExStyle | WS_EX_LAYERED); - - SetBackgroundColor(RGB(0, 0, 0)); - SetLayeredWindowAttributes(0, 130, LWA_ALPHA); - m_nStreamID = CAgoraObject::GetAgoraObject()->CreateMessageStream(); - - return TRUE; // return TRUE unless you set the focus to a control - // 쳣: OCX ҳӦ FALSE -} - -void CChatDlg::OnSize(UINT nType, int cx, int cy) -{ - CDialogEx::OnSize(nType, cx, cy); - - // TODO: ڴ˴Ϣ - if (::IsWindow(m_edtChatBox.GetSafeHwnd())) - m_edtChatBox.MoveWindow(1, cy - 21, cx - 2, 20); -} - - -BOOL CChatDlg::PreTranslateMessage(MSG* pMsg) -{ - // TODO: ڴרô/û - CString str; - - if (pMsg->message == WM_KEYDOWN){ - if (pMsg->wParam == VK_RETURN) { - m_edtChatBox.GetWindowText(str); - if (str.GetLength() > 0) { - CAgoraObject::GetAgoraObject()->SendChatMessage(m_nStreamID, str); - AddChatMessage(0, str); - m_edtChatBox.SetWindowText(_T("")); - } - } - - return FALSE; - } - - return CDialogEx::PreTranslateMessage(pMsg); -} - - -void CChatDlg::OnPaint() -{ - CPaintDC dc(this); // device context for painting - // TODO: ڴ˴Ϣ - // ΪͼϢ CDialogEx::OnPaint() - - int y = 100; - - POSITION pos = m_strMsgList.GetHeadPosition(); - dc.SetTextColor(RGB(0xFF, 0xFF, 0xFF)); - dc.SetBkColor(RGB(0, 0, 0)); - - while (pos != NULL) { - CString str = m_strMsgList.GetNext(pos); - dc.TextOut(20, y, str); - y -= 20; - } -} - -void CChatDlg::AddChatMessage(UINT nUID, LPCTSTR lpMessage) -{ - CString str; - - if (nUID != 0) - str.Format(_T("%d: %s"), nUID, lpMessage); - else - str.Format(_T("me: %s"), lpMessage); - - if (m_strMsgList.GetCount() >= 5) - m_strMsgList.RemoveTail(); - - m_strMsgList.AddHead(str); - - Invalidate(TRUE); -} - -void CChatDlg::ClearHistory() -{ - m_strMsgList.RemoveAll(); - - Invalidate(TRUE); -} \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/ChatDlg.h b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/ChatDlg.h deleted file mode 100644 index 2d931dcc..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/ChatDlg.h +++ /dev/null @@ -1,37 +0,0 @@ -#pragma once -#include "afxwin.h" -#include - -// CChatDlg Ի - -class CChatDlg : public CDialogEx -{ - DECLARE_DYNAMIC(CChatDlg) - -public: - CChatDlg(CWnd* pParent = NULL); // ׼캯 - virtual ~CChatDlg(); - -// Ի - enum { IDD = IDD_MESSAGE_DIALOG }; - - void AddChatMessage(UINT nUID, LPCTSTR lpMessage); - void ClearHistory(); - -protected: - virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV ֧ - virtual BOOL OnInitDialog(); - virtual BOOL PreTranslateMessage(MSG* pMsg); - - afx_msg void OnPaint(); - afx_msg void OnSize(UINT nType, int cx, int cy); - - DECLARE_MESSAGE_MAP() - - -private: - CEdit m_edtChatBox; - - CStringList m_strMsgList; - int m_nStreamID; -}; diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/DeviceDlg.cpp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/DeviceDlg.cpp deleted file mode 100644 index a80de87c..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/DeviceDlg.cpp +++ /dev/null @@ -1,385 +0,0 @@ -// DeviceDlg.cpp : ʵļ -// - -#include "stdafx.h" -#include "OpenVideoCall.h" -#include "DeviceDlg.h" -#include "afxdialogex.h" - - -// CDeviceDlg Ի - -IMPLEMENT_DYNAMIC(CDeviceDlg, CDialogEx) - -CDeviceDlg::CDeviceDlg(CWnd* pParent /*=NULL*/) - : CDialogEx(CDeviceDlg::IDD, pParent) -{ - -} - -CDeviceDlg::~CDeviceDlg() -{ -} - -void CDeviceDlg::DoDataExchange(CDataExchange* pDX) -{ - CDialogEx::DoDataExchange(pDX); - - DDX_Control(pDX, IDC_BTNCANCEL_DEVICE, m_btnCancel); - DDX_Control(pDX, IDC_BTNCONFIRM_DEVICE, m_btnConfirm); - - DDX_Control(pDX, IDC_SLDAIN_DEVICE, m_sldAInVol); - DDX_Control(pDX, IDC_SLDAOUT_DEVICE, m_sldAOutVol); - DDX_Control(pDX, IDC_SLKAIN_DEVICE, m_slkAudInTest); - DDX_Control(pDX, IDC_SLKAOUT_DEVICE, m_slkAudOutTest); - DDX_Control(pDX, IDC_SLKCAM_DEVICE, m_slkCamTest); - DDX_Control(pDX, IDC_SLKECHO_DEVICE, m_slkEchoTest); -} - - -BEGIN_MESSAGE_MAP(CDeviceDlg, CDialogEx) - ON_WM_PAINT() - ON_WM_SHOWWINDOW() - ON_BN_CLICKED(IDC_BTNCANCEL_DEVICE, &CDeviceDlg::OnBnClickedBtncancelDevice) - ON_BN_CLICKED(IDC_BTNCONFIRM_DEVICE, &CDeviceDlg::OnBnClickedBtnconfirmDevice) - ON_MESSAGE(WM_MSGID(EID_AUDIO_VOLUME_INDICATION), &CDeviceDlg::OnEIDAudioVolumeIndication) - - ON_STN_CLICKED(IDC_SLKAIN_DEVICE, &CDeviceDlg::OnStnClickedSlkainDevice) - ON_STN_CLICKED(IDC_SLKAOUT_DEVICE, &CDeviceDlg::OnStnClickedSlkaoutDevice) - ON_STN_CLICKED(IDC_SLKCAM_DEVICE, &CDeviceDlg::OnStnClickedSlkcamDevice) - ON_STN_CLICKED(IDC_SLKECHO_DEVICE, &CDeviceDlg::OnStnClickedSlkechoDevice) - -END_MESSAGE_MAP() - - -// CDeviceDlg Ϣ -void CDeviceDlg::OnPaint() -{ - CPaintDC dc(this); - - DrawClient(&dc); -} - -BOOL CDeviceDlg::OnInitDialog() -{ - CDialogEx::OnInitDialog(); - - // TODO: ڴӶijʼ - m_lpRtcEngine = CAgoraObject::GetEngine(); - - m_ftDes.CreateFont(15, 0, 0, 0, FW_NORMAL, FALSE, FALSE, 0, ANSI_CHARSET, OUT_DEFAULT_PRECIS, CLIP_DEFAULT_PRECIS, DEFAULT_QUALITY, DEFAULT_PITCH | FF_SWISS, _T("Arial")); - m_ftLink.CreateFont(17, 0, 0, 0, FW_NORMAL, FALSE, TRUE, 0, ANSI_CHARSET, OUT_DEFAULT_PRECIS, CLIP_DEFAULT_PRECIS, DEFAULT_QUALITY, DEFAULT_PITCH | FF_SWISS, _T("Arial")); - m_ftBtn.CreateFont(16, 0, 0, 0, FW_NORMAL, FALSE, FALSE, 0, ANSI_CHARSET, OUT_DEFAULT_PRECIS, CLIP_DEFAULT_PRECIS, DEFAULT_QUALITY, DEFAULT_PITCH | FF_SWISS, _T("Arial")); - - m_wndVideoTest.Create(NULL, NULL, WS_CHILD | WS_VISIBLE, CRect(0, 0, 300, 40), this, IDC_VIDEOTEST_DEVICE); - m_wndVideoTest.SetVolRange(100); - - m_cbxAIn.Create(WS_CHILD | WS_VISIBLE, CRect(0, 0, 300, 40), this, IDC_CMBAIN_DEVICE); - m_cbxAOut.Create(WS_CHILD | WS_VISIBLE, CRect(0, 0, 300, 40), this, IDC_CMBAOUT_DEVICE); - m_cbxCam.Create(WS_CHILD | WS_VISIBLE, CRect(0, 0, 300, 40), this, IDC_CMBCAM_DEVICE); - m_penFrame.CreatePen(PS_SOLID, 1, RGB(0xD8, 0xD8, 0xD8)); - - SetBackgroundColor(RGB(0xFF, 0xFF, 0xFF), TRUE); - InitCtrls(); - - return TRUE; // return TRUE unless you set the focus to a control - // 쳣: OCX ҳӦ FALSE -} - -void CDeviceDlg::EnableDeviceTest(BOOL bEnable) -{ - m_slkAudInTest.EnableWindow(bEnable); - m_slkAudOutTest.EnableWindow(bEnable); - m_slkCamTest.EnableWindow(bEnable); -} - -void CDeviceDlg::InitCtrls() -{ - CRect ClientRect; - - MoveWindow(0, 0, 512, 640, 1); - CenterWindow(); - - GetClientRect(&ClientRect); - - m_cbxAIn.SetFaceColor(RGB(0xFF, 0xFF, 0xFF), RGB(0xFF, 0xFF, 0xFF)); - m_cbxAIn.MoveWindow(160, 65, 215, 22, TRUE); - m_cbxAOut.SetFaceColor(RGB(0xFF, 0xFF, 0xFF), RGB(0xFF, 0xFF, 0xFF)); - m_cbxAOut.MoveWindow(160, 195, 215, 22, TRUE); - m_cbxCam.SetFaceColor(RGB(0xFF, 0xFF, 0xFF), RGB(0xFF, 0xFF, 0xFF)); - m_cbxCam.MoveWindow(160, 325, 215, 22, TRUE); - m_sldAInVol.MoveWindow(155, 110, 285, 24, TRUE); - m_sldAOutVol.MoveWindow(155, 245, 285, 24, TRUE); - m_wndVideoTest.MoveWindow(155, 378, 192, 120, TRUE); - - m_slkAudInTest.SetFont(&m_ftLink); - m_slkAudInTest.MoveWindow(405, 65, 72, 40, TRUE); - m_slkAudOutTest.SetFont(&m_ftLink); - m_slkAudOutTest.MoveWindow(405, 200, 72, 40, TRUE); - m_slkCamTest.SetFont(&m_ftLink); - m_slkCamTest.MoveWindow(405, 325, 72, 40, TRUE); - m_slkEchoTest.SetFont(&m_ftLink); - m_slkEchoTest.MoveWindow(405, 425, 72, 40, TRUE); - - m_btnCancel.MoveWindow(66, ClientRect.Height() - 88, 180, 36, TRUE); -// m_btnCancel.EnableRoundCorner(TRUE); - - m_btnConfirm.MoveWindow(266, ClientRect.Height() - 88, 180, 36, TRUE); -// m_btnConfirm.EnableRoundCorner(TRUE); - - m_cbxAIn.SetButtonImage(IDB_CMBBTN, 12, 12, RGB(0xFF, 0x00, 0xFF)); - m_cbxAOut.SetButtonImage(IDB_CMBBTN, 12, 12, RGB(0xFF, 0x00, 0xFF)); - m_cbxCam.SetButtonImage(IDB_CMBBTN, 12, 12, RGB(0xFF, 0x00, 0xFF)); - m_cbxAIn.SetFont(&m_ftDes); - m_cbxAOut.SetFont(&m_ftDes); - m_cbxCam.SetFont(&m_ftDes); - - m_slkAudInTest.SetWindowText(LANG_STR("IDS_DEVICE_BTNTEST")); - m_slkAudOutTest.SetWindowText(LANG_STR("IDS_DEVICE_BTNTEST")); - m_slkCamTest.SetWindowText(LANG_STR("IDS_DEVICE_BTNTEST")); - - m_btnCancel.SetBorderColor(RGB(0xD8, 0xD8, 0xD8), RGB(0x00, 0xA0, 0xE9), RGB(0x00, 0xA0, 0xE9), RGB(0xCC, 0xCC, 0xCC)); - m_btnCancel.SetBackColor(RGB(0xFF, 0xFF, 0xFF), RGB(0xFF, 0xFF, 0xFF), RGB(0xFF, 0xFF, 0xFF), RGB(0xFF, 0xFF, 0xFF)); - m_btnCancel.SetFont(&m_ftBtn); - m_btnCancel.SetTextColor(RGB(0x55, 0x58, 0x5A), RGB(0x00, 0xA0, 0xE9), RGB(0x00, 0xA0, 0xE9), RGB(0xCC, 0xCC, 0xCC)); - m_btnCancel.SetWindowText(LANG_STR("IDS_DEVICE_CANCEL")); - - m_btnConfirm.SetBackColor(RGB(0x00, 0xA0, 0xE9), RGB(0x05, 0x78, 0xAA), RGB(0x05, 0x78, 0xAA), RGB(0xE6, 0xE6, 0xE6)); - m_btnConfirm.SetFont(&m_ftBtn); - m_btnConfirm.SetTextColor(RGB(0xFF, 0xFF, 0xFF), RGB(0xFF, 0xFF, 0xFF), RGB(0xFF, 0xFF, 0xFF), RGB(0xCC, 0xCC, 0xCC)); - m_btnConfirm.SetWindowText(LANG_STR("IDS_DEVICE_CONFIRM")); - - m_sldAInVol.SetThumbBitmap(IDB_SLDTHUMB_NORMAL, IDB_SLDTHUMB_HOT, IDB_SLDTHUMB_HOT, RGB(0xFF, 0, 0xFF)); - m_sldAInVol.SetRange(0, 255); - - m_sldAOutVol.SetThumbBitmap(IDB_SLDTHUMB_NORMAL, IDB_SLDTHUMB_HOT, IDB_SLDTHUMB_HOT, RGB(0xFF, 0, 0xFF)); - m_sldAOutVol.SetRange(0, 255); -} - -void CDeviceDlg::DrawClient(CDC *lpDC) -{ - CRect rcText; - CRect rcClient; - LPCTSTR lpString = NULL; - - GetClientRect(&rcClient); - - CFont* defFont = lpDC->SelectObject(&m_ftDes); - lpDC->SetBkColor(RGB(0xFF, 0xFF, 0xFF)); - lpDC->SetTextColor(RGB(0xD8, 0xD8, 0xD8)); - - lpDC->SelectObject(&m_penFrame); - rcText.SetRect(rcClient.Width() / 2 - 190, 60, rcClient.Width() / 2 + 130, 92); - lpDC->RoundRect(&rcText, CPoint(32, 32)); - lpString = LANG_STR("IDS_DEVICE_AUDIOIN"); - lpDC->TextOut(80, 69, lpString, _tcslen(lpString)); - - rcText.SetRect(rcClient.Width() / 2 - 190, 190, rcClient.Width() / 2 + 130, 222); - lpDC->RoundRect(&rcText, CPoint(32, 32)); - lpString = LANG_STR("IDS_DEVICE_AUDIOOUT"); - lpDC->TextOut(80, 199, lpString, _tcslen(lpString)); - - rcText.SetRect(rcClient.Width() / 2 - 190, 320, rcClient.Width() / 2 + 130, 352); - lpDC->RoundRect(&rcText, CPoint(32, 32)); - lpString = LANG_STR("IDS_DEVICE_CAMERA"); - lpDC->TextOut(80, 329, lpString, _tcslen(lpString)); - - lpString = LANG_STR("IDS_DEVICE_VOLUME"); - lpDC->SetTextColor(RGB(0x00, 0x00, 0x00)); - lpDC->TextOut(66, 115, lpString, _tcslen(lpString)); - lpDC->TextOut(66, 250, lpString, _tcslen(lpString)); - - lpDC->SelectObject(defFont); -} - -void CDeviceDlg::OnShowWindow(BOOL bShow, UINT nStatus) -{ - CDialogEx::OnShowWindow(bShow, nStatus); - - // TODO: ڴ˴Ϣ - if (!bShow) { - m_agPlayout.Close(); - m_agAudioin.Close(); - m_agCamera.Close(); - - CAgoraObject::GetAgoraObject()->EnableEchoTest(FALSE); - m_slkEchoTest.SetWindowText(_T("EchoTest")); - - return; - } - - CString strDeviceName; - CString strDeviceID; - CString strCurID; - - m_agPlayout.Create(m_lpRtcEngine); - m_agAudioin.Create(m_lpRtcEngine); - m_agCamera.Create(m_lpRtcEngine); - - m_sldAOutVol.SetPos(m_agPlayout.GetVolume()); - m_sldAInVol.SetPos(m_agAudioin.GetVolume()); - - m_cbxAOut.ResetContent(); - strCurID = m_agPlayout.GetCurDeviceID(); - for (UINT nIndex = 0; nIndex < m_agPlayout.GetDeviceCount(); nIndex++){ - m_agPlayout.GetDevice(nIndex, strDeviceName, strDeviceID); - m_cbxAOut.InsertString(nIndex, strDeviceName); - - if (strCurID == strDeviceID) - m_cbxAOut.SetCurSel(nIndex); - } - - m_cbxAIn.ResetContent(); - strCurID = m_agAudioin.GetCurDeviceID(); - for (UINT nIndex = 0; nIndex < m_agAudioin.GetDeviceCount(); nIndex++){ - m_agAudioin.GetDevice(nIndex, strDeviceName, strDeviceID); - m_cbxAIn.InsertString(nIndex, strDeviceName); - - if (strCurID == strDeviceID) - m_cbxAIn.SetCurSel(nIndex); - } - - m_cbxCam.ResetContent(); - strCurID = m_agCamera.GetCurDeviceID(); - for (UINT nIndex = 0; nIndex < m_agCamera.GetDeviceCount(); nIndex++){ - m_agCamera.GetDevice(nIndex, strDeviceName, strDeviceID); - m_cbxCam.InsertString(nIndex, strDeviceName); - - if (strCurID == strDeviceID) - m_cbxCam.SetCurSel(nIndex); - } -} - - -BOOL CDeviceDlg::PreTranslateMessage(MSG* pMsg) -{ - // TODO: ڴרô/û - if (pMsg->message == WM_KEYDOWN){ - switch (pMsg->wParam){ - case VK_ESCAPE: - OnBnClickedBtncancelDevice(); - return FALSE; - case VK_RETURN: - OnBnClickedBtnconfirmDevice(); - return FALSE; - } - } - - return CDialogEx::PreTranslateMessage(pMsg); -} - - -void CDeviceDlg::OnBnClickedBtncancelDevice() -{ - // TODO: ڴӿؼ֪ͨ - m_agAudioin.TestAudInputDevice(NULL, FALSE); - m_slkAudInTest.SetWindowText(LANG_STR("IDS_DEVICE_BTNTEST")); - - m_agPlayout.TestPlaybackDevice(ID_TEST_AUDIO, FALSE); - m_slkAudOutTest.SetWindowText(LANG_STR("IDS_DEVICE_BTNTEST")); - - m_agCamera.TestCameraDevice(NULL, FALSE); - m_slkCamTest.SetWindowText(LANG_STR("IDS_DEVICE_BTNTEST")); - - CDialogEx::OnCancel(); -} - - -void CDeviceDlg::OnBnClickedBtnconfirmDevice() -{ - // TODO: ڴӿؼ֪ͨ - int nCurSel = 0; - CString strDeviceName; - CString strDeviceID; - - m_agAudioin.SetVolume(m_sldAInVol.GetPos()); - m_agPlayout.SetVolume(m_sldAOutVol.GetPos()); - - m_agAudioin.TestAudInputDevice(NULL, FALSE); - m_slkAudInTest.SetWindowText(LANG_STR("IDS_DEVICE_BTNTEST")); - nCurSel = m_cbxAIn.GetCurSel(); - if (nCurSel != -1) { - m_agAudioin.GetDevice(nCurSel, strDeviceName, strDeviceID); - m_agAudioin.SetCurDevice(strDeviceID); - } - - - m_agPlayout.TestPlaybackDevice(ID_TEST_AUDIO, FALSE); - m_slkAudOutTest.SetWindowText(LANG_STR("IDS_DEVICE_BTNTEST")); - nCurSel = m_cbxAOut.GetCurSel(); - if (nCurSel != -1) { - m_agPlayout.GetDevice(nCurSel, strDeviceName, strDeviceID); - m_agPlayout.SetCurDevice(strDeviceID); - } - - m_agCamera.TestCameraDevice(NULL, FALSE); - m_slkCamTest.SetWindowText(LANG_STR("IDS_DEVICE_BTNTEST")); - nCurSel = m_cbxCam.GetCurSel(); - if (nCurSel != -1) { - m_agCamera.GetDevice(nCurSel, strDeviceName, strDeviceID); - m_agCamera.SetCurDevice(strDeviceID); - } - - CDialogEx::OnOK(); -} - -LRESULT CDeviceDlg::OnEIDAudioVolumeIndication(WPARAM wParam, LPARAM lParam) -{ - LPAGE_AUDIO_VOLUME_INDICATION lpData = (LPAGE_AUDIO_VOLUME_INDICATION)wParam; - m_wndVideoTest.SetCurVol(lpData->totalVolume); - - delete lpData; - - return 0; -} - -void CDeviceDlg::OnStnClickedSlkainDevice() -{ - // TODO: ڴӿؼ֪ͨ - if (m_agAudioin.IsTesting()) { - m_agAudioin.TestAudInputDevice(NULL, FALSE); - m_slkAudInTest.SetWindowText(LANG_STR("IDS_DEVICE_BTNTEST")); - } - else { - m_agAudioin.TestAudInputDevice(GetSafeHwnd(), TRUE); - m_slkAudInTest.SetWindowText(LANG_STR("IDS_DEVICE_BTNTESTOFF")); - } -} - -void CDeviceDlg::OnStnClickedSlkaoutDevice() -{ - if (m_agPlayout.IsTesting()) { - m_agPlayout.TestPlaybackDevice(ID_TEST_AUDIO, FALSE); - m_slkAudOutTest.SetWindowText(LANG_STR("IDS_DEVICE_BTNTEST")); - } - else { - m_agPlayout.TestPlaybackDevice(ID_TEST_AUDIO, TRUE); - m_slkAudOutTest.SetWindowText(LANG_STR("IDS_DEVICE_BTNTESTOFF")); - } -} - -void CDeviceDlg::OnStnClickedSlkcamDevice() -{ - if (m_agCamera.IsTesting()) { - m_agCamera.TestCameraDevice(NULL, FALSE); - m_slkCamTest.SetWindowText(LANG_STR("IDS_DEVICE_BTNTEST")); - } - else { - m_agCamera.TestCameraDevice(m_wndVideoTest.GetVideoSafeHwnd(), TRUE); - m_slkCamTest.SetWindowText(LANG_STR("IDS_DEVICE_BTNTESTOFF")); - } -} - -void CDeviceDlg::OnStnClickedSlkechoDevice() -{ - CAgoraObject *lpAgoraObject = CAgoraObject::GetAgoraObject(); - - if (lpAgoraObject->IsEchoTesting()) { - lpAgoraObject->EnableEchoTest(FALSE); - m_slkEchoTest.SetWindowText(_T("EchoTest")); - } - else{ - lpAgoraObject->EnableEchoTest(TRUE); - m_slkEchoTest.SetWindowText(_T("StopEcho")); - } -} \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/DeviceDlg.h b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/DeviceDlg.h deleted file mode 100644 index a8a74a26..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/DeviceDlg.h +++ /dev/null @@ -1,82 +0,0 @@ -#pragma once -#include "AGButton.h" -#include "AGComboBox.h" -#include "AGSliderCtrl.h" -#include "AGLinkCtrl.h" -#include "AGVideoTestWnd.h" - -#include "AgoraPlayoutManager.h" -#include "AgoraAudInputManager.h" -#include "AgoraCameraManager.h" - -// CDeviceDlg Ի - -class CDeviceDlg : public CDialogEx -{ - DECLARE_DYNAMIC(CDeviceDlg) - -public: - CDeviceDlg(CWnd* pParent = NULL); // ׼캯 - virtual ~CDeviceDlg(); - -// Ի - enum { IDD = IDD_DEVICE_DIALOG }; - - void EnableDeviceTest(BOOL bEnable); - -protected: - virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV ֧ - virtual BOOL OnInitDialog(); - virtual BOOL PreTranslateMessage(MSG* pMsg); - - afx_msg void OnPaint(); - afx_msg void OnShowWindow(BOOL bShow, UINT nStatus); - - afx_msg void OnStnClickedSlkainDevice(); - afx_msg void OnStnClickedSlkaoutDevice(); - afx_msg void OnStnClickedSlkcamDevice(); - afx_msg void OnStnClickedSlkechoDevice(); - - afx_msg void OnBnClickedBtncancelDevice(); - afx_msg void OnBnClickedBtnconfirmDevice(); - - afx_msg LRESULT OnEIDAudioVolumeIndication(WPARAM wParam, LPARAM lParam); - - DECLARE_MESSAGE_MAP() - -protected: - void InitCtrls(); - void DrawClient(CDC *lpDC); - - -private: - CFont m_ftLink; - CFont m_ftDes; // text in ctrl - CFont m_ftBtn; // button - - CPen m_penFrame; - CAGComboBox m_cbxAIn; - CAGComboBox m_cbxAOut; - CAGComboBox m_cbxCam; - - CAGLinkCtrl m_slkAudInTest; - CAGLinkCtrl m_slkAudOutTest; - CAGLinkCtrl m_slkCamTest; - CAGLinkCtrl m_slkEchoTest; - - CAGSliderCtrl m_sldAInVol; - CAGSliderCtrl m_sldAOutVol; - - CAGButton m_btnCancel; - CAGButton m_btnConfirm; - - CAGVideoTestWnd m_wndVideoTest; - -private: - IRtcEngine *m_lpRtcEngine; - CAgoraPlayoutManager m_agPlayout; - CAgoraAudInputManager m_agAudioin; - CAgoraCameraManager m_agCamera; - -public: -}; diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/DskcapsetDlg.cpp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/DskcapsetDlg.cpp deleted file mode 100644 index 465b476e..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/DskcapsetDlg.cpp +++ /dev/null @@ -1,120 +0,0 @@ -// DskcapsetDlg.cpp : ʵļ -// - -#include "stdafx.h" -#include "OpenVideoCall.h" -#include "DskcapsetDlg.h" -#include "afxdialogex.h" - - -// CDskcapsetDlg Ի - -IMPLEMENT_DYNAMIC(CDskcapsetDlg, CDialogEx) - -CDskcapsetDlg::CDskcapsetDlg(CWnd* pParent /*=NULL*/) - : CDialogEx(CDskcapsetDlg::IDD, pParent) - , m_nBitrate(0) -{ - -} - -CDskcapsetDlg::~CDskcapsetDlg() -{ -} - -void CDskcapsetDlg::DoDataExchange(CDataExchange* pDX) -{ - CDialogEx::DoDataExchange(pDX); - DDX_Control(pDX, IDC_CMBFRMRATE_TB, m_cbxCaptureFPS); -} - - -BEGIN_MESSAGE_MAP(CDskcapsetDlg, CDialogEx) - ON_WM_SHOWWINDOW() -END_MESSAGE_MAP() - - -// CDskcapsetDlg Ϣ - -int CDskcapsetDlg::GetCaptureFPS() -{ - int nSel = m_cbxCaptureFPS.GetCurSel(); - - if (nSel == -1) - return 15; - - return nSel + 1; -} - -void CDskcapsetDlg::SetCaptureRect(LPCRECT lpRect) -{ - ASSERT(lpRect->left != lpRect->right); - ASSERT(lpRect->top != lpRect->bottom); - - if (lpRect->left == lpRect->right || lpRect->top == lpRect->bottom) - return; - - m_rcRegion.CopyRect(lpRect); - - CString str; - str.Format(_T("\nleft:%d,top:%d, right:%d, bottom:%d\n"), lpRect->left, lpRect->top, lpRect->right, lpRect->bottom); - OutputDebugString(str); - SetDlgItemInt(IDC_EDX_TB, m_rcRegion.left); - SetDlgItemInt(IDC_EDY_TB, m_rcRegion.top); - SetDlgItemInt(IDC_EDW_TB, m_rcRegion.Width()); - SetDlgItemInt(IDC_EDH_TB, m_rcRegion.Height()); -} - -void CDskcapsetDlg::GetCaptureRect(LPRECT lpRect) -{ - lpRect->left = m_rcRegion.left; - lpRect->right = m_rcRegion.right; - lpRect->top = m_rcRegion.top; - lpRect->bottom = m_rcRegion.bottom; - - int bitrate = GetDlgItemInt(IDC_EDBITRATE_TB, NULL, TRUE); - if (bitrate > 0) - m_nBitrate = bitrate; - m_rcRegion.left = GetDlgItemInt(IDC_EDX_TB, NULL, TRUE); - m_rcRegion.top = GetDlgItemInt(IDC_EDY_TB, NULL, TRUE); - m_rcRegion.right = m_rcRegion.left + GetDlgItemInt(IDC_EDW_TB, NULL, TRUE); - m_rcRegion.bottom = m_rcRegion.top + GetDlgItemInt(IDC_EDH_TB, NULL, TRUE); -} - -BOOL CDskcapsetDlg::OnInitDialog() -{ - CDialogEx::OnInitDialog(); - - // TODO: ڴӶijʼ - CString str; - for (int nIndex = 0; nIndex < 15; nIndex++) { - str.Format(_T("%d fps"), nIndex + 1); - m_cbxCaptureFPS.InsertString(nIndex, str); - } - m_cbxCaptureFPS.SetCurSel(14); - - return TRUE; // return TRUE unless you set the focus to a control - // 쳣: OCX ҳӦ FALSE -} - - -void CDskcapsetDlg::OnShowWindow(BOOL bShow, UINT nStatus) -{ - CDialogEx::OnShowWindow(bShow, nStatus); - - // TODO: ڴ˴Ϣ - - if (!bShow) { - m_nBitrate = GetDlgItemInt(IDC_EDBITRATE_TB, NULL, TRUE); - m_rcRegion.left = GetDlgItemInt(IDC_EDX_TB, NULL, TRUE); - m_rcRegion.top = GetDlgItemInt(IDC_EDY_TB, NULL, TRUE); - m_rcRegion.right = m_rcRegion.left + GetDlgItemInt(IDC_EDW_TB, NULL, TRUE); - m_rcRegion.bottom = m_rcRegion.top + GetDlgItemInt(IDC_EDH_TB, NULL, TRUE); - } - else { - SetDlgItemInt(IDC_EDX_TB, m_rcRegion.left); - SetDlgItemInt(IDC_EDY_TB, m_rcRegion.top); - SetDlgItemInt(IDC_EDW_TB, m_rcRegion.Width()); - SetDlgItemInt(IDC_EDH_TB, m_rcRegion.Height()); - } -} \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/DskcapsetDlg.h b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/DskcapsetDlg.h deleted file mode 100644 index eb5d525f..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/DskcapsetDlg.h +++ /dev/null @@ -1,41 +0,0 @@ -#pragma once -#include "afxwin.h" - - -// CDskcapsetDlg Ի - -class CDskcapsetDlg : public CDialogEx -{ - DECLARE_DYNAMIC(CDskcapsetDlg) - -public: - CDskcapsetDlg(CWnd* pParent = NULL); // ׼캯 - virtual ~CDskcapsetDlg(); - -// Ի - enum { IDD = IDD_DSKCAPTB_DIALOG }; - - int GetCaptureFPS(); - void SetCaptureRect(LPCRECT lpRect); - void GetCaptureRect(LPRECT lpRect); - - int GetBitrate() { return m_nBitrate; }; - -protected: - virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV ֧ - virtual BOOL OnInitDialog(); - - afx_msg void OnShowWindow(BOOL bShow, UINT nStatus); - - - DECLARE_MESSAGE_MAP() - -// data -private: - CRect m_rcRegion; - int m_nBitrate; - -// controls -private: - CComboBox m_cbxCaptureFPS; -}; diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/EnterChannelDlg.cpp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/EnterChannelDlg.cpp deleted file mode 100644 index 77381973..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/EnterChannelDlg.cpp +++ /dev/null @@ -1,229 +0,0 @@ -// EnterChannelDlg.cpp : ʵļ -// - -#include "stdafx.h" -#include "OpenVideoCall.h" -#include "EnterChannelDlg.h" - - -#include "afxdialogex.h" - - -// CEnterChannelDlg Ի - -IMPLEMENT_DYNAMIC(CEnterChannelDlg, CDialogEx) - -CEnterChannelDlg::CEnterChannelDlg(CWnd* pParent /*=NULL*/) - : CDialogEx(CEnterChannelDlg::IDD, pParent) -{ - -} - -CEnterChannelDlg::~CEnterChannelDlg() -{ -} - -void CEnterChannelDlg::DoDataExchange(CDataExchange* pDX) -{ - CDialogEx::DoDataExchange(pDX); - DDX_Control(pDX, IDC_EDCHNAME_CHANNEL, m_ctrChannel); - DDX_Control(pDX, IDC_EDENCKEY_CHANNEL, m_ctrEncKey); - DDX_Control(pDX, IDC_BTNTEST_CHANNEL, m_btnTest); - DDX_Control(pDX, IDC_BTNJOIN_CHANNEL, m_btnJoin); - DDX_Control(pDX, IDC_BTNSET_CHANNEL, m_btnSetup); -} - - -BEGIN_MESSAGE_MAP(CEnterChannelDlg, CDialogEx) - ON_WM_NCHITTEST() - ON_WM_PAINT() - ON_BN_CLICKED(IDC_BTNTEST_CHANNEL, &CEnterChannelDlg::OnBnClickedBtntestChannel) - ON_BN_CLICKED(IDC_BTNJOIN_CHANNEL, &CEnterChannelDlg::OnBnClickedBtnjoinChannel) - ON_BN_CLICKED(IDC_BTNSET_CHANNEL, &CEnterChannelDlg::OnBnClickedBtnsetChannel) -END_MESSAGE_MAP() - - -// CEnterChannelDlg Ϣ -BOOL CEnterChannelDlg::PreTranslateMessage(MSG* pMsg) -{ - if (pMsg->message == WM_KEYDOWN){ - switch (pMsg->wParam){ - case VK_ESCAPE: - return FALSE; - case VK_RETURN: - OnBnClickedBtnjoinChannel(); - return FALSE; - } - } - - return CDialogEx::PreTranslateMessage(pMsg); -} - -BOOL CEnterChannelDlg::OnInitDialog() -{ - CDialogEx::OnInitDialog(); - - // TODO: ڴӶijʼ - m_ftEncy.CreateFont(17, 0, 0, 0, FW_BOLD, FALSE, FALSE, 0, ANSI_CHARSET, OUT_DEFAULT_PRECIS, CLIP_DEFAULT_PRECIS, DEFAULT_QUALITY, DEFAULT_PITCH | FF_SWISS, _T("Arial")); - m_ftHead.CreateFont(15, 0, 0, 0, FW_NORMAL, FALSE, FALSE, 0, ANSI_CHARSET, OUT_DEFAULT_PRECIS, CLIP_DEFAULT_PRECIS, DEFAULT_QUALITY, DEFAULT_PITCH | FF_SWISS, _T("Arial")); - m_ftDesc.CreateFont(15, 0, 0, 0, FW_NORMAL, FALSE, FALSE, 0, ANSI_CHARSET, OUT_DEFAULT_PRECIS, CLIP_DEFAULT_PRECIS, DEFAULT_QUALITY, DEFAULT_PITCH | FF_SWISS, _T("Arial")); - m_ftBtn.CreateFont(16, 0, 0, 0, FW_NORMAL, FALSE, FALSE, 0, ANSI_CHARSET, OUT_DEFAULT_PRECIS, CLIP_DEFAULT_PRECIS, DEFAULT_QUALITY, DEFAULT_PITCH | FF_SWISS, _T("Arial")); - m_penFrame.CreatePen(PS_SOLID, 1, RGB(0xD8, 0xD8, 0xD8)); - - m_dlgDevice.Create(CDeviceDlg::IDD, this); - m_dlgDevice.EnableDeviceTest(TRUE); - - SetBackgroundColor(RGB(0xFF, 0xFF, 0xFF)); - InitCtrls(); - - return TRUE; // return TRUE unless you set the focus to a control - // 쳣: OCX ҳӦ FALSE -} - -void CEnterChannelDlg::InitCtrls() -{ - CRect ClientRect; - -// MoveWindow(0, 0, 320, 450, 1); - GetClientRect(&ClientRect); - - m_ctrChannel.MoveWindow(ClientRect.Width()/2-160, 128, 320, 22, TRUE); - m_ctrChannel.SetFont(&m_ftHead); - m_ctrChannel.SetCaretPos(CPoint(12, 148)); - m_ctrChannel.ShowCaret(); - m_ctrChannel.SetTip(LANG_STR("IDS_CHN_CHTIP")); - - m_ctrEncKey.MoveWindow(ClientRect.Width() / 2 - 160, 176, 160, 22, TRUE); - m_ctrEncKey.SetFont(&m_ftHead); - m_ctrEncKey.SetCaretPos(CPoint(12, 148)); - m_ctrEncKey.ShowCaret(); - m_ctrEncKey.SetTip(LANG_STR("IDS_CHN_KEYTIP")); - - m_cmbEncType.Create(WS_CHILD | WS_VISIBLE | CBS_DROPDOWNLIST | CBS_OWNERDRAWVARIABLE, CRect(ClientRect.Width() / 2 + 1, 168, 180, 32), this, IDC_CMBENCTYPE_CHANNEL); - m_cmbEncType.MoveWindow(ClientRect.Width() / 2 + 50, 173, 120, 22, TRUE); - m_cmbEncType.SetFont(&m_ftHead); - - m_cmbEncType.SetButtonImage(IDB_CMBBTN, 12, 12, RGB(0xFF, 0x00, 0xFF)); - m_cmbEncType.SetFaceColor(RGB(0xFF, 0xFF, 0xFF), RGB(0xFF, 0xFF, 0xFF)); - m_cmbEncType.InsertString(0, LANG_STR("IDS_CHN_AES128XTS")); - m_cmbEncType.InsertString(1, LANG_STR("IDS_CHN_AES256XTS")); - m_cmbEncType.SetCurSel(0); - - m_btnJoin.MoveWindow(ClientRect.Width() / 2 - 180, 212, 360, 36, TRUE); - m_btnTest.MoveWindow(ClientRect.Width() / 2 - 180, 314, 108, 36, TRUE); - m_btnSetup.MoveWindow(ClientRect.Width()/2-60, 314, 240, 36, TRUE); - - - m_btnJoin.SetBackColor(RGB(0x00, 0xA0, 0xE9), RGB(0x05, 0x78, 0xAA), RGB(0x05, 0x78, 0xAA), RGB(0xE6, 0xE6, 0xE6)); - m_btnJoin.SetFont(&m_ftBtn); - m_btnJoin.SetTextColor(RGB(0xFF, 0xFF, 0xFF), RGB(0xFF, 0xFF, 0xFF), RGB(0xFF, 0xFF, 0xFF), RGB(0xCC, 0xCC, 0xCC)); - m_btnJoin.SetWindowText(LANG_STR("IDS_CHN_BTJOIN")); - - m_btnTest.SetBorderColor(RGB(0xD8, 0xD8, 0xD8), RGB(0x00, 0xA0, 0xE9), RGB(0x00, 0xA0, 0xE9), RGB(0xCC, 0xCC, 0xCC)); - m_btnTest.SetBackColor(RGB(0xFF, 0xFF, 0xFF), RGB(0xFF, 0xFF, 0xFF), RGB(0xFF, 0xFF, 0xFF), RGB(0xFF, 0xFF, 0xFF)); - m_btnTest.SetFont(&m_ftBtn); - m_btnTest.SetTextColor(RGB(0x55, 0x58, 0x5A), RGB(0x00, 0xA0, 0xE9), RGB(0x00, 0xA0, 0xE9), RGB(0xCC, 0xCC, 0xCC)); - m_btnTest.SetWindowText(LANG_STR("IDS_CHN_BTTEST")); - - m_btnSetup.SetBorderColor(RGB(0xD8, 0xD8, 0xD8), RGB(0x00, 0xA0, 0xE9), RGB(0x00, 0xA0, 0xE9), RGB(0xCC, 0xCC, 0xCC)); - m_btnSetup.SetBackColor(RGB(0xFF, 0xFF, 0xFF), RGB(0xFF, 0xFF, 0xFF), RGB(0xFF, 0xFF, 0xFF), RGB(0xFF, 0xFF, 0xFF)); - m_btnSetup.SetFont(&m_ftBtn); - m_btnSetup.SetTextColor(RGB(0x55, 0x58, 0x5A), RGB(0x00, 0xA0, 0xE9), RGB(0x00, 0xA0, 0xE9), RGB(0xCC, 0xCC, 0xCC)); - m_btnSetup.SetWindowText(_T("1920*1080,15fps, 3mbps")); - - CMFCButton::EnableWindowsTheming(FALSE); -} - -void CEnterChannelDlg::OnPaint() -{ - CPaintDC dc(this); // device context for painting - - DrawClient(&dc); -} - - -void CEnterChannelDlg::DrawClient(CDC *lpDC) -{ - CRect rcText; - CRect rcClient; - LPCTSTR lpString = NULL; - - GetClientRect(&rcClient); - - CFont* defFont = lpDC->SelectObject(&m_ftHead); - lpDC->SetBkColor(RGB(0xFF, 0xFF, 0xFF)); - lpDC->SetTextColor(RGB(0x44, 0x45, 0x46)); - lpString = LANG_STR("IDS_CHN_TITLE"); - lpDC->TextOut(12, 10, lpString, _tcslen(lpString)); - - lpDC->SelectObject(&m_penFrame); - rcText.SetRect(rcClient.Width() / 2 - 188, 120, rcClient.Width() / 2 + 172, 152); - lpDC->RoundRect(&rcText, CPoint(32, 32)); - - rcText.OffsetRect(0, 48); - lpDC->RoundRect(&rcText, CPoint(32, 32)); - - lpDC->SelectObject(&m_ftDesc); - lpDC->SetTextColor(RGB(0x91, 0x96, 0xA0)); - lpString = LANG_STR("IDS_CHN_DSC1"); - lpDC->TextOut(12, 45, lpString, _tcslen(lpString)); - lpString = LANG_STR("IDS_CHN_DSC2"); - lpDC->TextOut(12, 65, lpString, _tcslen(lpString)); - - lpDC->SetTextColor(RGB(0xD8, 0xD8, 0xD8)); - lpString = LANG_STR("IDS_CHN_ENCTYPE"); - lpDC->TextOut(240, 176, lpString, _tcslen(lpString)); - - lpDC->SelectObject(defFont); - - // Done with the font. Delete the font object. - // font.DeleteObject(); -} - -void CEnterChannelDlg::OnBnClickedBtntestChannel() -{ - // TODO: ڴӿؼ֪ͨ - m_dlgDevice.ShowWindow(SW_SHOW); - m_dlgDevice.CenterWindow(); -} - - -void CEnterChannelDlg::OnBnClickedBtnjoinChannel() -{ - // TODO: ڴӿؼ֪ͨ -// CString str = CAgoraObject::GetAgoraObject()->GetCallID(); - CString strKey; - - m_ctrEncKey.GetWindowText(strKey); - if (strKey.GetLength() > 0) - CAgoraObject::GetAgoraObject()->SetEncryptionSecret(strKey, m_cmbEncType.GetCurSel()); - GetParent()->SendMessage(WM_JOINCHANNEL, 0, 0); -} - - -void CEnterChannelDlg::OnBnClickedBtnsetChannel() -{ - // TODO: ڴӿؼ֪ͨ -// SHORT sKeyStat = ::GetAsyncKeyState(VK_CONTROL); - - GetParent()->SendMessage(WM_GONEXT, 0, 0); -} - -CString CEnterChannelDlg::GetChannelName() -{ - CString strChannelName; - - m_ctrChannel.GetWindowText(strChannelName); - - return strChannelName; -} - -void CEnterChannelDlg::SetVideoString(LPCTSTR lpVideoString) -{ - m_btnSetup.SetWindowText(lpVideoString); -} - -void CEnterChannelDlg::CleanEncryptionSecret() -{ - m_ctrEncKey.SetWindowText(_T("")); -} \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/EnterChannelDlg.h b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/EnterChannelDlg.h deleted file mode 100644 index b0a221d8..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/EnterChannelDlg.h +++ /dev/null @@ -1,58 +0,0 @@ -#pragma once -#include "AGButton.h" -#include "AGEdit.h" -#include "AGComboBox.h" -#include "DeviceDlg.h" -#include "afxwin.h" - -// CEnterChannelDlg Ի - -class CEnterChannelDlg : public CDialogEx -{ - DECLARE_DYNAMIC(CEnterChannelDlg) - -public: - CEnterChannelDlg(CWnd* pParent = NULL); // ׼캯 - virtual ~CEnterChannelDlg(); - - CString GetChannelName(); - - void SetVideoString(LPCTSTR lpVideoString); - void CleanEncryptionSecret(); - -// Ի - enum { IDD = IDD_ENTERCHANNEL_DIALOG }; - -protected: - virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV ֧ - virtual BOOL OnInitDialog(); - virtual BOOL PreTranslateMessage(MSG* pMsg); - - afx_msg void OnPaint(); - afx_msg void OnBnClickedBtntestChannel(); - afx_msg void OnBnClickedBtnjoinChannel(); - afx_msg void OnBnClickedBtnsetChannel(); - - DECLARE_MESSAGE_MAP() - -protected: - void InitCtrls(); - void DrawClient(CDC *lpDC); - -private: - CAGEdit m_ctrChannel; - CAGEdit m_ctrEncKey; - CAGComboBox m_cmbEncType; - CAGButton m_btnTest; - CAGButton m_btnJoin; - CAGButton m_btnSetup; - - CFont m_ftEncy; - CFont m_ftHead; - CFont m_ftDesc; - CFont m_ftBtn; - - CPen m_penFrame; - - CDeviceDlg m_dlgDevice; -}; diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/LanguageSet.cpp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/LanguageSet.cpp deleted file mode 100644 index e14b6294..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/LanguageSet.cpp +++ /dev/null @@ -1,108 +0,0 @@ -#include "stdafx.h" -#include "LanguageSet.h" - -CLanguageSet *CLanguageSet::m_lpLanguageSet = NULL; -TCHAR CLanguageSet::m_szSelfPath[MAX_PATH]; - -CLanguageSet::CLanguageSet() -{ -} - - -CLanguageSet::~CLanguageSet() -{ -} - -CLanguageSet *CLanguageSet::GetInstance() -{ - if (CLanguageSet::m_lpLanguageSet == NULL) - CLanguageSet::m_lpLanguageSet = new CLanguageSet(); - - ::GetModuleFileName(NULL, CLanguageSet::m_szSelfPath, MAX_PATH); - LPTSTR lpLastSlash = _tcsrchr(CLanguageSet::m_szSelfPath, _T('\\')) + 1; - _tcscpy_s(lpLastSlash, MAX_PATH, _T("Language\\")); - - CString strLanguageName = CLanguageSet::m_lpLanguageSet->GetCurrentLanguage(); - - CLanguageSet::m_lpLanguageSet->LoadLanguageModule(strLanguageName); - - return CLanguageSet::m_lpLanguageSet; -} - -void CLanguageSet::CloseInstance() -{ - CLanguageSet::m_lpLanguageSet->UnloadLanguageModule(); - delete CLanguageSet::m_lpLanguageSet; - - CLanguageSet::m_lpLanguageSet = NULL; -} - -CString CLanguageSet::GetCurrentLanguage() -{ - CString strCurrent; - TCHAR szProfilePath[MAX_PATH]; - - _tcscpy_s(szProfilePath, MAX_PATH, CLanguageSet::m_szSelfPath); - _tcscat_s(szProfilePath, MAX_PATH, _T("Language.ini")); - - ::GetPrivateProfileString(_T("language"), _T("current"), _T("english.dll"), strCurrent.GetBuffer(MAX_PATH), MAX_PATH, szProfilePath); - - strCurrent.ReleaseBuffer(); - - return strCurrent; -} - -BOOL CLanguageSet::SetCurrentLanguage(LPCTSTR lpLanguageName) -{ - TCHAR szProfilePath[MAX_PATH]; - TCHAR szModulePath[MAX_PATH]; - - _tcscpy_s(szProfilePath, MAX_PATH, CLanguageSet::m_szSelfPath); - _tcscat_s(szProfilePath, _T("Language.ini")); - - _tcscpy_s(szModulePath, MAX_PATH, CLanguageSet::m_szSelfPath); - _tcscat_s(szModulePath, MAX_PATH, lpLanguageName); - _tcscat_s(szModulePath, MAX_PATH, _T(".dll")); - if (::GetFileAttributes(szModulePath) == INVALID_FILE_ATTRIBUTES) - return FALSE; - - return ::WritePrivateProfileString(_T("language"), _T("current"), lpLanguageName, szProfilePath); -} - -LPCTSTR CLanguageSet::GetString(LPCSTR lpStringID) -{ - ASSERT(m_hLanguageModule != NULL); - - LPCTSTR *lpStrAddr = (LPCTSTR *)::GetProcAddress(m_hLanguageModule, lpStringID); - - return *lpStrAddr;// ::GetProcAddress(m_hLanguageModule, lpStringID); -} - -BOOL CLanguageSet::LoadLanguageModule(LPCTSTR lpLanguageName) -{ - TCHAR szModulePath[MAX_PATH]; - LPTSTR lpLastSlash = NULL; - - _tcscpy_s(szModulePath, MAX_PATH, CLanguageSet::m_szSelfPath); - - if (lpLanguageName == NULL) - _tcscat_s(szModulePath, MAX_PATH, GetCurrentLanguage()); - else - _tcscat_s(szModulePath, MAX_PATH, lpLanguageName); - -// _tcscat_s(szModulePath, MAX_PATH, _T(".dll")); - if (::GetFileAttributes(szModulePath) == INVALID_FILE_ATTRIBUTES) - return FALSE; - - m_hLanguageModule = ::LoadLibrary(szModulePath); - - return m_hLanguageModule != NULL ? TRUE : FALSE; -} - -void CLanguageSet::UnloadLanguageModule() -{ - if (m_hLanguageModule != NULL) - ::FreeLibrary(m_hLanguageModule); - - m_hLanguageModule = NULL; -} \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/LanguageSet.h b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/LanguageSet.h deleted file mode 100644 index 41509993..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/LanguageSet.h +++ /dev/null @@ -1,29 +0,0 @@ -#pragma once - -//#define LANGUAGE_SET_MSG _T("SNOWWALKER_LANGSET_MSG") - -#define LANG_STR(lpStringID) (CLanguageSet::GetInstance()->GetString(lpStringID)) - -class CLanguageSet -{ -protected: - CLanguageSet(); - ~CLanguageSet(); - -public: - static CLanguageSet *GetInstance(); - static void CloseInstance(); - - CString GetCurrentLanguage(); - BOOL SetCurrentLanguage(LPCTSTR lpLanguageName); - LPCTSTR GetString(LPCSTR lpStringID); - - BOOL LoadLanguageModule(LPCTSTR lpLanguageName = NULL); - void UnloadLanguageModule(); - -private: - HMODULE m_hLanguageModule; - static CLanguageSet *m_lpLanguageSet; - static TCHAR m_szSelfPath[MAX_PATH]; -}; - diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/LogoDlg.cpp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/LogoDlg.cpp deleted file mode 100644 index d66f0c54..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/LogoDlg.cpp +++ /dev/null @@ -1,168 +0,0 @@ -// LogoDlg.cpp : ʵļ -// - -#include "stdafx.h" -#include "OpenVideoCall.h" -#include "LogoDlg.h" -#include "afxdialogex.h" - - -// CLogoDlg Ի - -IMPLEMENT_DYNAMIC(CLogoDlg, CDialogEx) - -CLogoDlg::CLogoDlg(CWnd* pParent /*=NULL*/) - : CDialogEx(CLogoDlg::IDD, pParent) -{ - m_hIcon = AfxGetApp()->LoadIcon(IDR_MAINFRAME); - m_bmpLogo.LoadBitmap(IDB_LOGO); -} - -CLogoDlg::~CLogoDlg() -{ -} - -void CLogoDlg::DoDataExchange(CDataExchange* pDX) -{ - CDialogEx::DoDataExchange(pDX); - DDX_Control(pDX, IDC_BTNMIN, m_btnMin); - DDX_Control(pDX, IDC_BTNCLOSE, m_btnClose); -} - - -BEGIN_MESSAGE_MAP(CLogoDlg, CDialogEx) - ON_WM_NCHITTEST() - ON_BN_CLICKED(IDC_BTNMIN, &CLogoDlg::OnBnClickedBtnmin) - ON_BN_CLICKED(IDC_BTNCLOSE, &CLogoDlg::OnBnClickedBtnclose) - ON_WM_TIMER() - ON_WM_PAINT() -END_MESSAGE_MAP() - - -// CLogoDlg Ϣ - -BOOL CLogoDlg::OnInitDialog() -{ - CDialogEx::OnInitDialog(); - - // Add "About..." menu item to system menu. - - // Set the icon for this dialog. The framework does this automatically - // when the application's main window is not a dialog - SetIcon(m_hIcon, TRUE); // Set big icon - SetIcon(m_hIcon, FALSE); // Set small icon - - // TODO: Add extra initialization here - m_ftTitle.CreateFont(16, 0, 0, 0, FW_BOLD, FALSE, FALSE, 0, ANSI_CHARSET, OUT_DEFAULT_PRECIS, CLIP_DEFAULT_PRECIS, DEFAULT_QUALITY, DEFAULT_PITCH | FF_SWISS, _T("Arial")); - m_ftDescp.CreateFont(15, 0, 0, 0, FW_BOLD, FALSE, FALSE, 0, ANSI_CHARSET, OUT_DEFAULT_PRECIS, CLIP_DEFAULT_PRECIS, DEFAULT_QUALITY, DEFAULT_PITCH | FF_SWISS, _T("Arial")); - - SetBackgroundColor(RGB(0xFF, 0xFF, 0xFF)); - InitCtrls(); - - AnimateWindow(500, AW_BLEND | AW_SLIDE); - m_nTimerID = SetTimer(1, 1000, NULL); - - Invalidate(TRUE); - - return TRUE; // return TRUE unless you set the focus to a control -} - -void CLogoDlg::InitCtrls() -{ - CRect ClientRect; - - MoveWindow(0, 0, 720, 600, 1); - GetClientRect(&ClientRect); - CenterWindow(); - - m_btnMin.MoveWindow(ClientRect.Width() - 46, 1, 22, 22, TRUE); - m_btnClose.MoveWindow(ClientRect.Width() - 23, 1, 22, 22, TRUE); - - m_btnMin.SetBackImage(IDB_BTNMIN, RGB(0xFF, 0, 0xFF)); - m_btnClose.SetBackImage(IDB_BTNCLOSE, RGB(0xFF, 0, 0xFF)); - - CMFCButton::EnableWindowsTheming(FALSE); -} - - -LRESULT CLogoDlg::OnNcHitTest(CPoint point) -{ - // TODO: ڴϢ/Ĭֵ - LRESULT lResult = CDialogEx::OnNcHitTest(point); - if (lResult == HTCLIENT && ::GetAsyncKeyState(MK_LBUTTON) < 0) - lResult = HTCAPTION; - - return lResult; -} - -void CLogoDlg::DrawClient(CDC *lpDC) -{ - CRect rcText; - CDC memDC; - - LPCTSTR lpString = NULL; - CFont* defFont = lpDC->SelectObject(&m_ftTitle); - - memDC.CreateCompatibleDC(lpDC); - memDC.SelectObject(&m_bmpLogo); - lpString = LANG_STR("IDS_TITLE"); - lpDC->FillSolidRect(0, 0, 720, 24, RGB(0, 161, 230)); - lpDC->SetBkColor(RGB(0x00, 0x9E, 0xEB)); - lpDC->SetTextColor(RGB(0xFF, 0xFF, 0xFF)); - rcText.SetRect(5, 5, 20, 400); - lpDC->TextOut(320, 3, lpString, _tcslen(lpString)); - - lpDC->SetBkColor(RGB(0xFF, 0xFF, 0xFF)); - lpDC->SetTextColor(RGB(0x91, 0x96, 0xA0)); - lpDC->TextOut(305, 316, lpString, _tcslen(lpString)); - - lpString = LANG_STR("IDS_LOGO_DESC"); - lpDC->SelectObject(&m_ftDescp); - lpDC->SetTextColor(RGB(0x00, 0x9D, 0xEB)); - lpDC->TextOut(255, 348, lpString, _tcslen(lpString)); - - lpDC->BitBlt(294, 224, 132, 72, &memDC, 0, 0, SRCCOPY); - - lpDC->SelectObject(defFont); -} - -void CLogoDlg::OnBnClickedBtnmin() -{ - // TODO: ڴӿؼ֪ͨ - ShowWindow(SW_MINIMIZE); -} - - -void CLogoDlg::OnBnClickedBtnclose() -{ - // TODO: ڴӿؼ֪ͨ -#ifdef DEBUG - AnimateWindow(3000, AW_BLEND | AW_HIDE | AW_SLIDE); -#else - AnimateWindow(1000, AW_BLEND | AW_HIDE | AW_SLIDE); -#endif - CDialogEx::OnCancel(); -} - - - -void CLogoDlg::OnTimer(UINT_PTR nIDEvent) -{ - // TODO: ڴϢ/Ĭֵ - if (nIDEvent == 1){ - PostMessage(WM_COMMAND, (WPARAM)IDCANCEL, NULL); - KillTimer(1); - } - - CDialogEx::OnTimer(nIDEvent); -} - - -void CLogoDlg::OnPaint() -{ - CPaintDC dc(this); // device context for painting - // TODO: ڴ˴Ϣ - // ΪͼϢ CDialogEx::OnPaint() - - DrawClient(&dc); -} diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/LogoDlg.h b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/LogoDlg.h deleted file mode 100644 index 66d3f076..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/LogoDlg.h +++ /dev/null @@ -1,48 +0,0 @@ -#pragma once -#include "AGButton.h" - -// CLogoDlg Ի - -class CLogoDlg : public CDialogEx -{ - DECLARE_DYNAMIC(CLogoDlg) - -public: - CLogoDlg(CWnd* pParent = NULL); // ׼캯 - virtual ~CLogoDlg(); - -// Ի - enum { IDD = IDD_LOGO_DIALOG }; - -protected: - HICON m_hIcon; - - // Generated message map functions - virtual BOOL OnInitDialog(); - virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV ֧ - afx_msg HCURSOR OnQueryDragIcon(); - afx_msg LRESULT OnNcHitTest(CPoint point); - - afx_msg void OnBnClickedBtnmin(); - afx_msg void OnBnClickedBtnclose(); - afx_msg void OnTimer(UINT_PTR nIDEvent); - afx_msg void OnPaint(); - - DECLARE_MESSAGE_MAP() - -protected: - void InitCtrls(); - void DrawClient(CDC *lpDC); - -private: - CAGButton m_btnMin; - CAGButton m_btnClose; - - CFont m_ftTitle; - CFont m_ftDescp; - - UINT_PTR m_nTimerID; - -private: - CBitmap m_bmpLogo; -}; diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/OpenVideoCall.cpp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/OpenVideoCall.cpp deleted file mode 100644 index 96ddb2f0..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/OpenVideoCall.cpp +++ /dev/null @@ -1,112 +0,0 @@ - -// AgoraVideoCall.cpp : Defines the class behaviors for the application. -// - -#include "stdafx.h" -#include "OpenVideoCall.h" -#include "LogoDlg.h" -#include "OpenVideoCallDlg.h" -#include "EnterChannelDlg.h" - -#ifdef _DEBUG -#define new DEBUG_NEW -#endif - - -// CAgoraVideoCallApp - -BEGIN_MESSAGE_MAP(COpenVideoCallApp, CWinApp) - ON_COMMAND(ID_HELP, &CWinApp::OnHelp) -END_MESSAGE_MAP() - - -// CAgoraVideoCallApp construction - -COpenVideoCallApp::COpenVideoCallApp() -{ - // support Restart Manager - m_dwRestartManagerSupportFlags = AFX_RESTART_MANAGER_SUPPORT_RESTART; - - // TODO: add construction code here, - // Place all significant initialization in InitInstance -} - - -// The one and only CAgoraVideoCallApp object - -COpenVideoCallApp theApp; - - -// CAgoraVideoCallApp initialization - -BOOL COpenVideoCallApp::InitInstance() -{ - // InitCommonControlsEx() is required on Windows XP if an application - // manifest specifies use of ComCtl32.dll version 6 or later to enable - // visual styles. Otherwise, any window creation will fail. - INITCOMMONCONTROLSEX InitCtrls; - InitCtrls.dwSize = sizeof(InitCtrls); - // Set this to include all the common control classes you want to use - // in your application. - InitCtrls.dwICC = ICC_WIN95_CLASSES; - InitCommonControlsEx(&InitCtrls); - - CWinApp::InitInstance(); - - - AfxEnableControlContainer(); - - // Create the shell manager, in case the dialog contains - // any shell tree view or shell list view controls. - CShellManager *pShellManager = new CShellManager; - - // Activate "Windows Native" visual manager for enabling themes in MFC controls - CMFCVisualManager::SetDefaultManager(RUNTIME_CLASS(CMFCVisualManagerWindows)); - - // Standard initialization - // If you are not using these features and wish to reduce the size - // of your final executable, you should remove from the following - // the specific initialization routines you do not need - // Change the registry key under which our settings are stored - // TODO: You should modify this string to be something appropriate - // such as the name of your company or organization - SetRegistryKey(_T("Local AppWizard-Generated Applications")); - CAgoraObject::EnableWhiteboardVer(TRUE); - CAgoraObject::EnableWhiteboardFeq(TRUE); - - INT_PTR nResponse = 0; - CLogoDlg Logo; - - nResponse = Logo.DoModal(); - COpenVideoCallDlg avcDlg; - - m_pMainWnd = &avcDlg; - nResponse = avcDlg.DoModal(); - - if (nResponse == IDOK) - { - // TODO: Place code here to handle when the dialog is - // dismissed with OK - } - else if (nResponse == IDCANCEL) - { - // TODO: Place code here to handle when the dialog is - // dismissed with Cancel - } - else if (nResponse == -1) - { - TRACE(traceAppMsg, 0, "Warning: dialog creation failed, so application is terminating unexpectedly.\n"); - TRACE(traceAppMsg, 0, "Warning: if you are using MFC controls on the dialog, you cannot #define _AFX_NO_MFC_CONTROLS_IN_DIALOGS.\n"); - } - - // Delete the shell manager created above. - if (pShellManager != NULL) - { - delete pShellManager; - } - - // Since the dialog has been closed, return FALSE so that we exit the - // application, rather than start the application's message pump. - return FALSE; -} - diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/OpenVideoCall.h b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/OpenVideoCall.h deleted file mode 100644 index 60f8018e..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/OpenVideoCall.h +++ /dev/null @@ -1,32 +0,0 @@ - -// OpenVideoCall.h : main header file for the PROJECT_NAME application -// - -#pragma once - -#ifndef __AFXWIN_H__ - #error "include 'stdafx.h' before including this file for PCH" -#endif - -#include "resource.h" // main symbols - - -// CAgoraVideoCallApp: -// See AgoraVideoCall.cpp for the implementation of this class -// - -class COpenVideoCallApp : public CWinApp -{ -public: - COpenVideoCallApp(); - -// Overrides -public: - virtual BOOL InitInstance(); - -// Implementation - - DECLARE_MESSAGE_MAP() -}; - -extern COpenVideoCallApp theApp; \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/OpenVideoCall.rc b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/OpenVideoCall.rc deleted file mode 100644 index 50da9f92b4cd802b13167461e82277c5b933932a..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 26802 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 - - - - Debug - Win32 - - - Debug - x64 - - - Release - Win32 - - - Release - x64 - - - - {26AF88DC-1933-4A1B-9991-21DF11DCE388} - AgoraVideoCall - MFCProj - - - - Application - true - v120_xp - Unicode - Static - - - Application - true - v120 - Unicode - Static - - - Application - false - v120_xp - true - Unicode - Static - - - Application - false - v120_xp - true - Unicode - Static - - - - - - - - - - - - - - - - - - - true - $(VC_IncludePath);$(WindowsSDK_IncludePath);../../../sdk/include;../sdk/include;../../sdk/include - $(VC_LibraryPath_x86);$(WindowsSDK_LibraryPath_x86);../../../sdk/lib;../sdk/lib;../../sdk/lib - - - true - $(VC_IncludePath);$(WindowsSDK_IncludePath);../../../sdk/include;../sdk/include;../../sdk/include - $(VC_LibraryPath_x64);$(WindowsSDK_LibraryPath_x64);../../../sdk/lib;../sdk/lib;../../sdk/lib - $(SolutionDir)\$(Configuration)\ - $(Configuration)\ - - - false - $(VC_ExecutablePath_x86);$(WindowsSdk_71A_ExecutablePath);$(WindowsSDK_ExecutablePath);$(VS_ExecutablePath);$(MSBuild_ExecutablePath);$(SystemRoot)\SysWow64;$(FxCopDir);$(PATH); - - $(VC_IncludePath);$(WindowsSdk_71A_IncludePath);$(MSBuild_ExecutablePath);$(VC_LibraryPath_x86); - $(VC_IncludePath);$(WindowsSdk_71A_IncludePath);../../../sdk/include;../sdk/include;../../sdk/include - $(VC_LibraryPath_x86);$(WindowsSdk_71A_LibraryPath_x86);../../../sdk/lib;../sdk/lib;../../sdk/lib - - - false - $(VC_IncludePath);$(WindowsSdk_71A_IncludePath);../../../sdk/include;../sdk/include;../../sdk/include - $(VC_LibraryPath_x64);$(WindowsSdk_71A_LibraryPath_x64);../../../sdk/lib;../sdk/lib;../../sdk/lib - $(SolutionDir)\$(Configuration)\ - $(Configuration)\ - - - - Use - Level3 - Disabled - WIN32;_WINDOWS;_DEBUG;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions) - true - - - Windows - true - - - false - true - _DEBUG;%(PreprocessorDefinitions) - - - 0x0409 - _DEBUG;%(PreprocessorDefinitions) - $(IntDir);%(AdditionalIncludeDirectories) - - - if exist ..\sdk (copy ..\sdk\dll\*.dll ..\Debug\) else if exist ..\..\..\sdk (copy ..\..\..\sdk\dll\*.dll ..\Debug\) - - - - - Use - Level3 - Disabled - WIN32;_WINDOWS;_DEBUG;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions) - true - - - Windows - true - - - false - _DEBUG;%(PreprocessorDefinitions) - - - 0x0409 - _DEBUG;%(PreprocessorDefinitions) - $(IntDir);%(AdditionalIncludeDirectories) - - - if exist ..\sdk (copy ..\sdk\dll\*.dll ..\Debug\) else if exist ..\..\..\sdk (copy ..\..\..\sdk\dll\*.dll ..\Debug\) - - - - - Level3 - Use - MaxSpeed - true - true - WIN32;_WINDOWS;NDEBUG;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions) - true - - - Windows - true - true - true - - - false - true - NDEBUG;%(PreprocessorDefinitions) - - - 0x0409 - NDEBUG;%(PreprocessorDefinitions) - $(IntDir);%(AdditionalIncludeDirectories) - - - if exist ..\sdk (copy ..\sdk\dll\*.dll ..\Release\) else if exist ..\..\..\sdk (copy ..\..\..\sdk\dll\*.dll ..\Release\) - - - - - Level3 - Use - MaxSpeed - true - true - WIN32;_WINDOWS;NDEBUG;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions) - true - - - Windows - true - true - true - - - false - NDEBUG;%(PreprocessorDefinitions) - - - 0x0409 - NDEBUG;%(PreprocessorDefinitions) - $(IntDir);%(AdditionalIncludeDirectories) - - - if exist ..\sdk (copy ..\sdk\dll\*.dll ..\Release\) else if exist ..\..\..\sdk (copy ..\..\..\sdk\dll\*.dll ..\Release\) - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Create - Create - Create - Create - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - {898289d0-0d57-4b8e-97ae-013114f85de9} - - - {de1d9363-5455-4448-8d69-d22be47f5a82} - - - - - - - - - - - diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/OpenVideoCall.vcxproj.filters b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/OpenVideoCall.vcxproj.filters deleted file mode 100644 index c334e18d..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/OpenVideoCall.vcxproj.filters +++ /dev/null @@ -1,441 +0,0 @@ - - - - - {037bfcf0-7fcd-4fbe-b0a1-0bbdbe0866d4} - - - {dd6bd31f-57a0-4970-9870-4cbe6ead6530} - - - {22427098-c248-4e25-8c81-dd62508cf969} - - - {f8fa6769-043b-462c-8c2f-587906eee318} - - - {0f1c5e51-801f-4f53-a0af-3cec416b9702} - - - {2c600536-0ba8-4ae7-af61-78ffa247aed6} - - - {3d18d002-94ff-47be-ac37-9421b990e85a} - - - {075d76ad-44ba-49b2-8b94-0d123ad2bbb8} - - - {72981e3b-6e49-43b0-b4e1-fdeb7568d012} - - - {6c1a4b26-8ded-4c5d-a541-a9ed38a22ee8} - - - {67DA6AB6-F800-4c08-8B7A-83BB121AAD01} - rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms - - - - - - - - Headers - - - Headers - - - Headers - - - UI\Language - - - UI\Ctrl - - - UI\Ctrl - - - UI\Ctrl - - - UI\Dialog - - - UI\Dialog - - - Headers - - - UI\Dialog - - - UI\Ctrl - - - UI\Ctrl - - - UI\Dialog - - - AgoraObject - - - UI\Dialog - - - AgoraObject - - - AgoraObject - - - AgoraObject - - - AgoraObject - - - AgoraObject - - - AgoraObject\Config - - - UI\Wnd - - - UI\Wnd - - - UI\Dialog - - - UI\Ctrl - - - UI\Dialog - - - AgoraObject\Filter - - - App - - - UI\Dialog - - - UI\Dialog - - - UI\Dialog - - - - - Headers - - - UI\Language - - - UI\Ctrl - - - UI\Ctrl - - - UI\Ctrl - - - UI\Dialog - - - UI\Dialog - - - UI\Dialog - - - UI\Ctrl - - - UI\Ctrl - - - UI\Dialog - - - AgoraObject - - - AgoraObject - - - UI\Dialog - - - AgoraObject - - - AgoraObject - - - AgoraObject - - - AgoraObject - - - AgoraObject\Config - - - UI\Wnd - - - UI\Wnd - - - UI\Dialog - - - UI\Ctrl - - - UI\Dialog - - - AgoraObject\Filter - - - App - - - UI\Dialog - - - UI\Dialog - - - UI\Dialog - - - - - Resources - - - - - Resources - - - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - Resources - - - - - Resources - - - \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/OpenVideoCall.vcxproj.user b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/OpenVideoCall.vcxproj.user deleted file mode 100644 index ef5ff2a1..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/OpenVideoCall.vcxproj.user +++ /dev/null @@ -1,4 +0,0 @@ - - - - \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/OpenVideoCallDlg.cpp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/OpenVideoCallDlg.cpp deleted file mode 100644 index 177dfd67..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/OpenVideoCallDlg.cpp +++ /dev/null @@ -1,362 +0,0 @@ - -// AgoraVideoCallDlg.cpp : implementation file -// - -#include "stdafx.h" -#include "OpenVideoCall.h" -#include "OpenVideoCallDlg.h" -#include "afxdialogex.h" - -#ifdef _DEBUG -#define new DEBUG_NEW -#endif - - -// CAgoraVideoCallDlg dialog - - - -COpenVideoCallDlg::COpenVideoCallDlg(CWnd* pParent /*=NULL*/) - : CDialogEx(COpenVideoCallDlg::IDD, pParent) -{ - m_hIcon = AfxGetApp()->LoadIcon(IDR_MAINFRAME); - m_nVideoSolution = 0; - - m_lpAgoraObject = NULL; - m_lpRtcEngine = NULL; - - m_nLastmileQuality = 0; -} - -void COpenVideoCallDlg::DoDataExchange(CDataExchange* pDX) -{ - CDialogEx::DoDataExchange(pDX); - DDX_Control(pDX, IDC_BTNMIN, m_btnMin); - DDX_Control(pDX, IDC_BTNCLOSE, m_btnClose); - - DDX_Control(pDX, IDC_LINKAGORA, m_linkAgora); -} - -BEGIN_MESSAGE_MAP(COpenVideoCallDlg, CDialogEx) - ON_WM_SYSCOMMAND() - ON_WM_PAINT() - ON_WM_QUERYDRAGICON() - ON_WM_NCHITTEST() - ON_MESSAGE(WM_GOBACK, &COpenVideoCallDlg::OnBackPage) - ON_MESSAGE(WM_GONEXT, &COpenVideoCallDlg::OnNextPage) - ON_MESSAGE(WM_JOINCHANNEL, &COpenVideoCallDlg::OnJoinChannel) - ON_MESSAGE(WM_LEAVECHANNEL, &COpenVideoCallDlg::OnLeaveChannel) - - ON_BN_CLICKED(IDC_BTNMIN, &COpenVideoCallDlg::OnBnClickedBtnmin) - ON_BN_CLICKED(IDC_BTNCLOSE, &COpenVideoCallDlg::OnBnClickedBtnclose) - - ON_MESSAGE(WM_MSGID(EID_LASTMILE_QUALITY), &COpenVideoCallDlg::OnLastmileQuality) - -END_MESSAGE_MAP() - - -// CAgoraVideoCallDlg message handlers -BOOL COpenVideoCallDlg::PreTranslateMessage(MSG* pMsg) -{ - if (pMsg->message == WM_KEYDOWN){ - switch (pMsg->wParam){ - case VK_ESCAPE: - case VK_RETURN: - return FALSE; - } - } - - return CDialogEx::PreTranslateMessage(pMsg); -} - -BOOL COpenVideoCallDlg::OnInitDialog() -{ - CDialogEx::OnInitDialog(); - - // Add "About..." menu item to system menu. - - // IDM_ABOUTBOX must be in the system command range. - ASSERT((IDM_ABOUTBOX & 0xFFF0) == IDM_ABOUTBOX); - ASSERT(IDM_ABOUTBOX < 0xF000); - - CMenu* pSysMenu = GetSystemMenu(FALSE); - if (pSysMenu != NULL) - { - BOOL bNameValid; - CString strAboutMenu; - bNameValid = strAboutMenu.LoadString(IDS_ABOUTBOX); - ASSERT(bNameValid); - if (!strAboutMenu.IsEmpty()) - { - pSysMenu->AppendMenu(MF_SEPARATOR); - pSysMenu->AppendMenu(MF_STRING, IDM_ABOUTBOX, strAboutMenu); - } - } - - // Set the icon for this dialog. The framework does this automatically - // when the application's main window is not a dialog - SetIcon(m_hIcon, TRUE); // Set big icon - SetIcon(m_hIcon, FALSE); // Set small icon - - // TODO: Add extra initialization here - m_ftTitle.CreateFont(16, 0, 0, 0, FW_BOLD, FALSE, FALSE, 0, ANSI_CHARSET, OUT_DEFAULT_PRECIS, CLIP_DEFAULT_PRECIS, DEFAULT_QUALITY, DEFAULT_PITCH | FF_SWISS, _T("Arial")); - m_ftLink.CreateFont(16, 0, 0, 0, FW_NORMAL, FALSE, TRUE, 0, ANSI_CHARSET, OUT_DEFAULT_PRECIS, CLIP_DEFAULT_PRECIS, DEFAULT_QUALITY, DEFAULT_PITCH | FF_SWISS, _T("Arial")); - m_ftDes.CreateFont(15, 0, 0, 0, FW_NORMAL, FALSE, FALSE, 0, ANSI_CHARSET, OUT_DEFAULT_PRECIS, CLIP_DEFAULT_PRECIS, DEFAULT_QUALITY, DEFAULT_PITCH | FF_SWISS, _T("Arial")); - m_ftPhone.CreateFont(15, 0, 0, 0, FW_BOLD, FALSE, FALSE, 0, ANSI_CHARSET, OUT_DEFAULT_PRECIS, CLIP_DEFAULT_PRECIS, DEFAULT_QUALITY, DEFAULT_PITCH | FF_SWISS, _T("Arial")); - - CString strAppID = CAgoraObject::LoadAppID(); - - if (_tcslen(strAppID) == 0) { - MessageBox(_T("Please define your own APP_ID in source code"), _T("information"), MB_OK | MB_ICONINFORMATION); - ::PostQuitMessage(0); - } - - m_lpAgoraObject = CAgoraObject::GetAgoraObject(strAppID); - m_lpRtcEngine = CAgoraObject::GetEngine(); - m_lpAgoraObject->EnableVideo(TRUE); - m_lpAgoraObject->SetLogFilePath(NULL); - m_lpAgoraObject->EnableNetworkTest(TRUE); - m_lpAgoraObject->SetMsgHandlerWnd(GetSafeHwnd()); - - SetBackgroundColor(RGB(0xFF, 0xFF, 0xFF)); - InitCtrls(); - InitChildDialog(); - - return TRUE; // return TRUE unless you set the focus to a control -} - -void COpenVideoCallDlg::InitCtrls() -{ - CRect ClientRect; - CBitmap bmpNetQuality; - - MoveWindow(0, 0, 720, 600, 1); - GetClientRect(&ClientRect); - - bmpNetQuality.LoadBitmap(IDB_NETWORK_QUALITY); - - m_imgNetQuality.Create(32, 32, ILC_COLOR24 | ILC_MASK, 6, 1); - m_imgNetQuality.Add(&bmpNetQuality, RGB(0xFF, 0, 0xFF)); - - m_btnMin.MoveWindow(ClientRect.Width() - 46, 1, 22, 22, TRUE); - m_btnClose.MoveWindow(ClientRect.Width() - 23, 1, 22, 22, TRUE); - m_linkAgora.MoveWindow(ClientRect.Width() / 2 - 110, ClientRect.Height()-55, 80, 20, TRUE); - - m_btnMin.SetBackImage(IDB_BTNMIN, RGB(0xFF, 0, 0xFF)); - m_btnClose.SetBackImage(IDB_BTNCLOSE, RGB(0xFF, 0, 0xFF)); - - m_linkAgora.SetFont(&m_ftLink); - m_linkAgora.SetURL(_T("http://www.agora.io")); - m_linkAgora.SetWindowText(LANG_STR("IDS_LOGO_AGORAWEB")); - CMFCButton::EnableWindowsTheming(FALSE); -} - -void COpenVideoCallDlg::InitChildDialog() -{ - CString str; - - m_dlgEnterChannel.Create(CEnterChannelDlg::IDD, this); - m_dlgSetup.Create(CSetupDlg::IDD, this); - m_dlgVideo.Create(CVideoDlg::IDD, this); - - m_dlgEnterChannel.MoveWindow(110, 70, 500, 450, TRUE); - m_dlgSetup.MoveWindow(110, 70, 500, 450, TRUE); - - m_dlgEnterChannel.ShowWindow(SW_SHOW); - m_lpCurDialog = &m_dlgEnterChannel; - - m_dlgEnterChannel.SetVideoString(m_dlgSetup.GetVideoSolutionDes()); - -// str.Format(_T("%d*%d,%dfps,%dKbps"), m_nVideoWidth, m_nVideoHeight, m_nFrameRate, m_nMaxRate); -// m_dlgEnterChannel.SetVideoString(str); -} - -void COpenVideoCallDlg::OnSysCommand(UINT nID, LPARAM lParam) -{ - CDialogEx::OnSysCommand(nID, lParam); -} - -// If you add a minimize button to your dialog, you will need the code below -// to draw the icon. For MFC applications using the document/view model, -// this is automatically done for you by the framework. - -void COpenVideoCallDlg::OnPaint() -{ - CPaintDC dc(this); // device context for painting - - if (IsIconic()) - { - SendMessage(WM_ICONERASEBKGND, reinterpret_cast(dc.GetSafeHdc()), 0); - - // Center icon in client rectangle - int cxIcon = GetSystemMetrics(SM_CXICON); - int cyIcon = GetSystemMetrics(SM_CYICON); - CRect rect; - GetClientRect(&rect); - int x = (rect.Width() - cxIcon + 1) / 2; - int y = (rect.Height() - cyIcon + 1) / 2; - - // Draw the icon - dc.DrawIcon(x, y, m_hIcon); - } - else - { - DrawClient(&dc); -// CDialogEx::OnPaint(); - } -} - -// The system calls this function to obtain the cursor to display while the user drags -// the minimized window. -HCURSOR COpenVideoCallDlg::OnQueryDragIcon() -{ - return static_cast(m_hIcon); -} - - - -LRESULT COpenVideoCallDlg::OnNcHitTest(CPoint point) -{ - // TODO: ڴϢ/Ĭֵ - LRESULT lResult = CDialogEx::OnNcHitTest(point); - if (lResult == HTCLIENT && ::GetAsyncKeyState(MK_LBUTTON) < 0) - lResult = HTCAPTION; - - return lResult; -} - -void COpenVideoCallDlg::DrawClient(CDC *lpDC) -{ - CRect rcText; - CRect rcClient; - LPCTSTR lpString = NULL; - CFont* defFont = lpDC->SelectObject(&m_ftTitle); - - m_imgNetQuality.Draw(lpDC, m_nLastmileQuality, CPoint(16, 40), ILD_NORMAL); - - GetClientRect(&rcClient); - lpDC->FillSolidRect(0, 0, 720, 24, RGB(0, 161, 230)); - lpDC->SetBkColor(RGB(0x00, 0x9E, 0xEB)); - lpDC->SetTextColor(RGB(0xFF, 0xFF, 0xFF)); - lpString = LANG_STR("IDS_TITLE"); - lpDC->TextOut(rcClient.Width()/2 - 80, 3, lpString, _tcslen(lpString)); - - lpDC->SelectObject(&m_ftDes); - lpDC->SetTextColor(RGB(0x91, 0x96, 0xA0)); - lpDC->SetBkColor(RGB(0xFF, 0xFF, 0xFF)); - lpString = LANG_STR("IDS_CONTACT"); - lpDC->TextOut(rcClient.Width() / 2-50, rcClient.Height() - 55, lpString, _tcslen(lpString)); - - lpDC->SelectObject(&m_ftPhone); - lpDC->SetTextColor(RGB(0x44, 0x45, 0x46)); - lpString = LANG_STR("IDS_PHONENUMBER"); - lpDC->TextOut(rcClient.Width() / 2 + 45, rcClient.Height() - 55, lpString, _tcslen(lpString)); - - lpDC->SelectObject(&m_ftDes); - lpDC->SetTextColor(RGB(0x91, 0x96, 0xA0)); - lpDC->SetBkColor(RGB(0xFF, 0xFF, 0xFF)); - lpString = AVC_VER;// _T("v1.3"); - CString strVersion = CAgoraObject::GetSDKVersionEx(); - - rcText.SetRect(0, rcClient.Height() - 30, rcClient.Width(), rcClient.Height() - 5); - lpDC->DrawText(strVersion, _tcslen(strVersion), &rcText, DT_CENTER | DT_SINGLELINE); - lpDC->SelectObject(defFont); -} - -void COpenVideoCallDlg::OnBnClickedBtnmin() -{ - // TODO: ڴӿؼ֪ͨ - ShowWindow(SW_MINIMIZE); -} - - -void COpenVideoCallDlg::OnBnClickedBtnclose() -{ - // TODO: ڴӿؼ֪ͨ - CDialogEx::OnCancel(); -} - -LRESULT COpenVideoCallDlg::OnBackPage(WPARAM wParam, LPARAM lParam) -{ - if (m_lpCurDialog == &m_dlgSetup) { - m_lpCurDialog->ShowWindow(SW_HIDE); - m_lpCurDialog = &m_dlgEnterChannel; - } - - CString str; - - m_dlgSetup.GetVideoSolution(); - m_dlgEnterChannel.SetVideoString(m_dlgSetup.GetVideoSolutionDes()); - - m_lpCurDialog->ShowWindow(SW_SHOW); - - return 0; -} - -LRESULT COpenVideoCallDlg::OnNextPage(WPARAM wParam, LPARAM lParam) -{ - m_lpCurDialog->ShowWindow(SW_HIDE); - if (m_lpCurDialog == &m_dlgEnterChannel) - m_lpCurDialog = &m_dlgSetup; - - m_lpCurDialog->ShowWindow(SW_SHOW); - - return 0; -} - -LRESULT COpenVideoCallDlg::OnJoinChannel(WPARAM wParam, LPARAM lParam) -{ - IRtcEngine *lpRtcEngine = CAgoraObject::GetEngine(); - CAgoraObject *lpAgoraObject = CAgoraObject::GetAgoraObject(); - - CString strChannelName = m_dlgEnterChannel.GetChannelName(); - if (strChannelName.GetLength() == 0) - return 0; - - m_dlgVideo.MoveWindow(0, 0, 960, 720, 1); - m_dlgVideo.ShowWindow(SW_SHOW); - m_dlgVideo.CenterWindow(); - - VideoCanvas vc; - - vc.uid = 0; - vc.view = m_dlgVideo.GetLocalVideoWnd(); - vc.renderMode = RENDER_MODE_TYPE::RENDER_MODE_FIT; - - //cancel setVideoProfile bitrate since version 2.1.0 - m_nVideoSolution = m_dlgSetup.GetVideoSolution(); - lpRtcEngine->setVideoProfile((VIDEO_PROFILE_TYPE)m_nVideoSolution, m_dlgSetup.IsWHSwap()); - lpAgoraObject->EnableVideo(TRUE); - - m_dlgVideo.SetWindowText(strChannelName); - lpRtcEngine->setupLocalVideo(vc); - lpRtcEngine->startPreview(); - - lpAgoraObject->JoinChannel(strChannelName,0, strlen(APP_TOKEN) > 0 ? APP_TOKEN:NULL); - lpAgoraObject->SetMsgHandlerWnd(m_dlgVideo.GetSafeHwnd()); - - return 0; -} - -LRESULT COpenVideoCallDlg::OnLeaveChannel(WPARAM wParam, LPARAM lParam) -{ - CAgoraObject *lpAgoraObject = CAgoraObject::GetAgoraObject(); - - lpAgoraObject->LeaveCahnnel(); - m_dlgEnterChannel.CleanEncryptionSecret(); - - return 0; -} - -LRESULT COpenVideoCallDlg::OnLastmileQuality(WPARAM wParam, LPARAM lParam) -{ - LPAGE_LASTMILE_QUALITY lpData = (LPAGE_LASTMILE_QUALITY)wParam; - - if (m_nLastmileQuality != lpData->quality) { - m_nLastmileQuality = lpData->quality; - InvalidateRect(CRect(16, 40, 48, 72), TRUE); - } - - delete lpData; - return 0; -} \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/OpenVideoCallDlg.h b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/OpenVideoCallDlg.h deleted file mode 100644 index 60a018af..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/OpenVideoCallDlg.h +++ /dev/null @@ -1,82 +0,0 @@ - -// AgoraVideoCallDlg.h : header file -// - -#pragma once - -#include "AGHyperlink.h" -#include "EnterChannelDlg.h" -#include "SetupDlg.h" -#include "VideoDlg.h" - -// CAgoraVideoCallDlg dialog -class COpenVideoCallDlg : public CDialogEx -{ -// Construction -public: - COpenVideoCallDlg(CWnd* pParent = NULL); // standard constructor - -// Dialog Data - enum { IDD = IDD_OPENVIDEOCALL_DIALOG }; - - protected: - virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV support - - -// Implementation -protected: - HICON m_hIcon; - - // Generated message map functions - virtual BOOL PreTranslateMessage(MSG* pMsg); - virtual BOOL OnInitDialog(); - afx_msg void OnSysCommand(UINT nID, LPARAM lParam); - afx_msg void OnPaint(); - afx_msg HCURSOR OnQueryDragIcon(); - afx_msg LRESULT OnNcHitTest(CPoint point); - - afx_msg void OnBnClickedBtnmin(); - afx_msg void OnBnClickedBtnclose(); - - afx_msg LRESULT OnBackPage(WPARAM wParam, LPARAM lParam); - afx_msg LRESULT OnNextPage(WPARAM wParam, LPARAM lParam); - afx_msg LRESULT OnJoinChannel(WPARAM wParam, LPARAM lParam); - afx_msg LRESULT OnLeaveChannel(WPARAM wParam, LPARAM lParam); - - afx_msg LRESULT OnLastmileQuality(WPARAM wParam, LPARAM lParam); - - - DECLARE_MESSAGE_MAP() - -protected: - void InitCtrls(); - void DrawClient(CDC *lpDC); - void InitChildDialog(); - -private: - CAGButton m_btnMin; - CAGButton m_btnClose; - - CAGHyperLink m_linkAgora; - - CDialogEx *m_lpCurDialog; - CEnterChannelDlg m_dlgEnterChannel; - CSetupDlg m_dlgSetup; - - CFont m_ftTitle; - CFont m_ftLink; - CFont m_ftDes; - CFont m_ftPhone; - CImageList m_imgNetQuality; - -private: - CVideoDlg m_dlgVideo; - CAgoraObject *m_lpAgoraObject; - IRtcEngine *m_lpRtcEngine; - -private: // data - int m_nCodecType; - int m_nVideoSolution; - - int m_nLastmileQuality; -}; diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/SetupDlg.cpp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/SetupDlg.cpp deleted file mode 100644 index e7867d0e..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/SetupDlg.cpp +++ /dev/null @@ -1,277 +0,0 @@ -// SetupDlg.cpp : ʵļ -// - -#include "stdafx.h" -#include "OpenVideoCall.h" -#include "SetupDlg.h" -#include "afxdialogex.h" - - -// CSetupDlg Ի - -IMPLEMENT_DYNAMIC(CSetupDlg, CDialogEx) - -CSetupDlg::CSetupDlg(CWnd* pParent /*=NULL*/) - : CDialogEx(CSetupDlg::IDD, pParent) -{ - -} - -CSetupDlg::~CSetupDlg() -{ -} - -void CSetupDlg::DoDataExchange(CDataExchange* pDX) -{ - CDialogEx::DoDataExchange(pDX); - DDX_Control(pDX, IDC_BTNCONFIRM_SETUP, m_btnConfirm); - DDX_Control(pDX, IDC_BTNCANCEL_SETUP, m_btnCancel); - DDX_Control(pDX, IDC_CKSAVESETTING_SETUP, m_ckSaveSettings); - DDX_Control(pDX, IDC_CKSWPWH_SETUP, m_ckSwapWH); -} - - -BEGIN_MESSAGE_MAP(CSetupDlg, CDialogEx) - ON_WM_PAINT() - ON_BN_CLICKED(IDC_BTNCONFIRM_SETUP, &CSetupDlg::OnBnClickedBtnconfirmSetup) - ON_BN_CLICKED(IDC_BTNCANCEL_SETUP, &CSetupDlg::OnBnClickedBtncancelSetup) -// ON_CBN_SELCHANGE(IDC_CMBRES_SETUP, &CSetupDlg::OnCbnSelchangeCmbresSetup) -// ON_CBN_SELCHANGE(IDC_CMBCODEC_SETUP, &CSetupDlg::OnCbnSelchangeCmbresSetup) - - ON_WM_HSCROLL() - ON_WM_LBUTTONDBLCLK() - -END_MESSAGE_MAP() - - -// CSetupDlg Ϣ - - -BOOL CSetupDlg::OnInitDialog() -{ - CDialogEx::OnInitDialog(); - - // TODO: ڴӶijʼ - m_ftHead.CreateFont(15, 0, 0, 0, FW_NORMAL, FALSE, FALSE, 0, ANSI_CHARSET, OUT_DEFAULT_PRECIS, CLIP_DEFAULT_PRECIS, DEFAULT_QUALITY, DEFAULT_PITCH | FF_SWISS, _T("Arial")); - m_ftDes.CreateFont(15, 0, 0, 0, FW_NORMAL, FALSE, FALSE, 0, ANSI_CHARSET, OUT_DEFAULT_PRECIS, CLIP_DEFAULT_PRECIS, DEFAULT_QUALITY, DEFAULT_PITCH | FF_SWISS, _T("Arial")); - m_ftBtn.CreateFont(16, 0, 0, 0, FW_NORMAL, FALSE, FALSE, 0, ANSI_CHARSET, OUT_DEFAULT_PRECIS, CLIP_DEFAULT_PRECIS, DEFAULT_QUALITY, DEFAULT_PITCH | FF_SWISS, _T("Arial")); - m_penFrame.CreatePen(PS_SOLID, 1, RGB(0xD8, 0xD8, 0xD8)); - - m_cbxVideoProfile.Create(WS_CHILD | WS_VISIBLE | CBS_DROPDOWNLIST, CRect(0, 0, 300, 40), this, IDC_CMBVDOPRF_SETUP); - SetBackgroundColor(RGB(0xFF, 0xFF, 0xFF), TRUE); - InitData(); - InitCtrls(); - - if (m_agConfig.IsAutoSaveEnabled()) - m_ckSaveSettings.SetCheck(TRUE); - else - m_ckSaveSettings.SetCheck(FALSE); - - return TRUE; // return TRUE unless you set the focus to a control - // 쳣: OCX ҳӦ FALSE -} - - -void CSetupDlg::InitCtrls() -{ - CRect ClientRect; - - MoveWindow(0, 0, 320, 450, 1); - GetClientRect(&ClientRect); - - int nResolutionIndex = 0; - CString str; - - m_cbxVideoProfile.MoveWindow(210, 125, 200, 22, TRUE); - m_cbxVideoProfile.SetFont(&m_ftDes); - m_cbxVideoProfile.SetButtonImage(IDB_CMBBTN, 12, 12, RGB(0xFF, 0x00, 0xFF)); - m_cbxVideoProfile.SetFaceColor(RGB(0xFF, 0xFF, 0xFF), RGB(0xFF, 0xFF, 0xFF)); - m_cbxVideoProfile.SetListMaxHeight(600); - - m_ckSwapWH.MoveWindow(75, 160, 20, 20, TRUE); - m_ckSaveSettings.MoveWindow(185, ClientRect.Height() - 120, 20, 20, TRUE); - - m_btnCancel.MoveWindow(ClientRect.Width() / 2 - 93, ClientRect.Height() - 58, 174, 36, TRUE); - m_btnConfirm.MoveWindow(ClientRect.Width() / 2 + 93, ClientRect.Height() - 58, 174, 36, TRUE); - - for (int nIndex = 0; nIndex < 31; nIndex++) { - m_cbxVideoProfile.InsertString(nIndex, m_szProfileDes[nIndex]); - m_cbxVideoProfile.SetItemData(nIndex, (DWORD_PTR)m_nProfileValue[nIndex]); - } - - m_btnCancel.SetBorderColor(RGB(0xD8, 0xD8, 0xD8), RGB(0x00, 0xA0, 0xE9), RGB(0x00, 0xA0, 0xE9), RGB(0xCC, 0xCC, 0xCC)); - m_btnCancel.SetBackColor(RGB(0xFF, 0xFF, 0xFF), RGB(0xFF, 0xFF, 0xFF), RGB(0xFF, 0xFF, 0xFF), RGB(0xFF, 0xFF, 0xFF)); - m_btnCancel.SetTextColor(RGB(0x55, 0x58, 0x5A), RGB(0x00, 0xA0, 0xE9), RGB(0x00, 0xA0, 0xE9), RGB(0xCC, 0xCC, 0xCC)); - - m_btnConfirm.SetBackColor(RGB(0, 160, 239), RGB(0, 160, 239), RGB(0, 160, 239), RGB(192, 192, 192)); - m_btnConfirm.SetFont(&m_ftBtn); - m_btnConfirm.SetTextColor(RGB(0xFF, 0xFF, 0xFF), RGB(0xFF, 0xC8, 0x64), RGB(0xFF, 0xC8, 0x64), RGB(0xCC, 0xCC, 0xCC)); - m_btnConfirm.SetWindowText(LANG_STR("IDS_SET_BTCONFIRM")); - - if (m_agConfig.IsAutoSaveEnabled()) - nResolutionIndex = m_agConfig.GetSolution(); - else - nResolutionIndex = 15; - - m_cbxVideoProfile.SetCurSel(nResolutionIndex); -} - -void CSetupDlg::InitData() -{ - m_szProfileDes[0] = _T("160x120 15fps"); //65kbps - m_nProfileValue[0] = 0; - m_szProfileDes[1] = _T("120x120 15fps"); //50kbps - m_nProfileValue[1] = 2; - - m_szProfileDes[2] = _T("320x180 15fps"); //140kbps - m_nProfileValue[2] = 10; - m_szProfileDes[3] = _T("180x180 15fps"); //100kbps - m_nProfileValue[3] = 12; - m_szProfileDes[4] = _T("240x180 15fps"); //120kbps - m_nProfileValue[4] = 13; - - m_szProfileDes[5] = _T("320x240 15fps"); //200kbps - m_nProfileValue[5] = 20; - m_szProfileDes[6] = _T("240x240 15fps"); //140kbps - m_nProfileValue[6] = 22; - m_szProfileDes[7] = _T("424x240 15fps"); //220kbps - m_nProfileValue[7] = 23; - - m_szProfileDes[8] = _T("640x360 15fps"); //400kbps - m_nProfileValue[8] = 30; - m_szProfileDes[9] = _T("360x360 15fps"); //260kbps - m_nProfileValue[9] = 32; - m_szProfileDes[10] = _T("640x360 30fps"); //600kbps - m_nProfileValue[10] = 33; - m_szProfileDes[11] = _T("360x360 30fps"); //400kbps - m_nProfileValue[11] = 35; - m_szProfileDes[12] = _T("480x360 15fps"); //320kbps - m_nProfileValue[12] = 36; - m_szProfileDes[13] = _T("480x360 30fps"); //490kbps - m_nProfileValue[13] = 37; - m_szProfileDes[14] = _T("640x360 15fps"); //800kbps - m_nProfileValue[14] = 38; - - m_szProfileDes[15] = _T("640x480 15fps"); //500kbps - m_nProfileValue[15] = 40; - m_szProfileDes[16] = _T("480x480 15fps"); //400kbps - m_nProfileValue[16] = 42; - m_szProfileDes[17] = _T("640x480 30fps"); //750kbps - m_nProfileValue[17] = 43; - m_szProfileDes[18] = _T("480x480 30fps"); //600kbps - m_nProfileValue[18] = 44; - m_szProfileDes[19] = _T("848x480 15fps"); //610kbps - m_nProfileValue[19] = 47; - m_szProfileDes[20] = _T("848x480 30fps"); //930kbps - m_nProfileValue[20] = 48; - - m_szProfileDes[21] = _T("1280x720 15fps"); //1130kbps - m_nProfileValue[21] = 50; - m_szProfileDes[22] = _T("1280x720 30fps"); //1710kbps - m_nProfileValue[22] = 52; - m_szProfileDes[23] = _T("960x720 15fps"); //910kbps - m_nProfileValue[23] = 54; - m_szProfileDes[24] = _T("960x720 30fps"); //1380kbps - m_nProfileValue[24] = 55; - - m_szProfileDes[25] = _T("1920x1080 15fps"); //2080kbps - m_nProfileValue[25] = 60; - m_szProfileDes[26] = _T("1920x1080 30fps"); //3150kbps - m_nProfileValue[26] = 62; - m_szProfileDes[27] = _T("1920x1080 60fps"); //4780kbps - m_nProfileValue[27] = 64; - m_szProfileDes[28] = _T("2560x1440 30fps"); //4850kbps - m_nProfileValue[28] = 66; - m_szProfileDes[29] = _T("3560x1440 60fps"); //7350kbps - m_nProfileValue[29] = 67; - - m_szProfileDes[30] = _T("3840x2160 30fps"); //8190kbps - m_nProfileValue[30] = 70; - m_szProfileDes[31] = _T("3840x2160 60fps"); //13500kbps - m_nProfileValue[31] = 72; -} - -void CSetupDlg::DrawClient(CDC *lpDC) -{ - CRect rcText; - CRect rcClient; - LPCTSTR lpString = NULL; - - GetClientRect(&rcClient); - - CFont* defFont = lpDC->SelectObject(&m_ftHead); - - lpDC->SelectObject(&m_penFrame); - rcText.SetRect(rcClient.Width() / 2 - 188, 120, rcClient.Width() / 2 + 172, 152); - lpDC->RoundRect(&rcText, CPoint(32, 32)); - - lpDC->SetBkColor(RGB(0xFF, 0xFF, 0xFF)); - lpDC->SetTextColor(RGB(0xD8, 0xD8, 0xD8)); - lpString = LANG_STR("IDS_SET_RESOLUTION"); - lpDC->TextOut(75, 128, lpString, _tcslen(lpString)); - - lpDC->SetTextColor(RGB(0x44, 0x45, 0x46)); - lpString = LANG_STR("IDS_SET_SWAPWH"); - lpDC->TextOut(100, 160, lpString, _tcslen(lpString)); - - lpString = LANG_STR("IDS_SET_SAVESETTING"); - lpDC->TextOut(205, rcClient.Height() - 118, lpString, _tcslen(lpString)); - - lpDC->SelectObject(defFont); -} - -void CSetupDlg::OnBnClickedBtnconfirmSetup() -{ - // TODO: ڴӿؼ֪ͨ - GetParent()->SendMessage(WM_GOBACK, 0, 0); - - if (m_ckSaveSettings.GetCheck() == TRUE) { - m_agConfig.EnableAutoSave(TRUE); - m_agConfig.SetSolution(m_cbxVideoProfile.GetCurSel()); - } - else - m_agConfig.EnableAutoSave(FALSE); -} - -void CSetupDlg::OnBnClickedBtncancelSetup() -{ - GetParent()->SendMessage(WM_GOBACK, 0, 0); -} - -void CSetupDlg::OnPaint() -{ - CPaintDC dc(this); // device context for painting - - DrawClient(&dc); -} - -int CSetupDlg::GetVideoSolution() -{ - int nIndex = m_cbxVideoProfile.GetCurSel(); - - return (int)m_cbxVideoProfile.GetItemData(nIndex); -} - -void CSetupDlg::SetVideoSolution(int nIndex) -{ - m_cbxVideoProfile.SetCurSel(nIndex); -} - -CString CSetupDlg::GetVideoSolutionDes() -{ - int nIndex = m_cbxVideoProfile.GetCurSel(); - if (nIndex == -1) - nIndex = 0; - - return (CString)m_szProfileDes[nIndex]; -} - -void CSetupDlg::SetWHSwap(BOOL bSwap) -{ - m_ckSwapWH.SetCheck(bSwap); -} - -BOOL CSetupDlg::IsWHSwap() -{ - return (BOOL)m_ckSwapWH.GetCheck(); -} \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/SetupDlg.h b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/SetupDlg.h deleted file mode 100644 index 05fc8a96..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/SetupDlg.h +++ /dev/null @@ -1,71 +0,0 @@ -#pragma once -#include "AGButton.h" -#include "AGComboBox.h" -#include "AGSliderCtrl.h" -#include "afxwin.h" - -#include "AGConfig.h" -// CSetupDlg Ի - -class CSetupDlg : public CDialogEx -{ - - DECLARE_DYNAMIC(CSetupDlg) - -public: - CSetupDlg(CWnd* pParent = NULL); // ׼캯 - virtual ~CSetupDlg(); - - void SetVideoSolution(int nIndex); - int GetVideoSolution(); - CString GetVideoSolutionDes(); - - void SetWHSwap(BOOL bSwap); - BOOL IsWHSwap(); - -// Ի - enum { IDD = IDD_SETUP_DIALOG }; - - typedef struct _AGVIDEO_PARAM - { - int nWidth; - int nHeight; - int nMinKPB; - int nMaxKPB; - - } AGNET_RATE_RANGE; - -protected: - virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV ֧ - virtual BOOL OnInitDialog(); - - afx_msg void OnPaint(); - afx_msg void OnBnClickedBtnconfirmSetup(); - afx_msg void OnBnClickedBtncancelSetup(); - DECLARE_MESSAGE_MAP() - -protected: - void InitCtrls(); - void InitData(); - void DrawClient(CDC *lpDC); - -private: - CAGButton m_btnCancel; - CAGButton m_btnConfirm; - CButton m_ckSwapWH; - CButton m_ckSaveSettings; - - CAGComboBox m_cbxVideoProfile; - - CFont m_ftHead; // title - CFont m_ftDes; // text in ctrl - CFont m_ftBtn; // button - CPen m_penFrame; - - LPTSTR m_szProfileDes[64]; - int m_nProfileValue[64]; - AGNET_RATE_RANGE m_agRateRange[13]; - -private: - CAGConfig m_agConfig; -}; diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/VideoDlg.cpp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/VideoDlg.cpp deleted file mode 100644 index 031284a8..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/VideoDlg.cpp +++ /dev/null @@ -1,1230 +0,0 @@ -// VideoDlg.cpp -// - -#include "stdafx.h" -#include "OpenVideoCall.h" -#include "VideoDlg.h" -#include "afxdialogex.h" -#include "AGEventDef.h" -#include "video_preprocessing_plugin.h" - -// CVideoDlg - -IMPLEMENT_DYNAMIC(CVideoDlg, CDialogEx) - -CVideoDlg::CVideoDlg(CWnd* pParent /*=NULL*/) - : CDialogEx(CVideoDlg::IDD, pParent) -{ - m_brHead.CreateSolidBrush(RGB(0, 160, 239)); - SetBackgroundColor(RGB(0x26, 0x26, 0x26)); - m_bLastStat = FALSE; - m_nScreenMode = SCREEN_VIDEO1; - m_bFullScreen = FALSE; - m_lpBigShowed = NULL; - m_bFilter = FALSE; - m_bShowInfo = FALSE; -} - -CVideoDlg::~CVideoDlg() -{ - m_brHead.DeleteObject(); -} - -void CVideoDlg::DoDataExchange(CDataExchange* pDX) -{ - CDialogEx::DoDataExchange(pDX); - - DDX_Control(pDX, IDC_BTNMIN_VIDEO, m_btnMin); - DDX_Control(pDX, IDC_BTNRSTO_VIDEO, m_btnRst); - DDX_Control(pDX, IDC_BTNCLOSE_VIDEO, m_btnClose); -} - - -BEGIN_MESSAGE_MAP(CVideoDlg, CDialogEx) - ON_WM_SIZE() - ON_WM_MOUSEMOVE() - ON_WM_PAINT() - ON_WM_NCHITTEST() - - ON_MESSAGE(WM_SHOWMODECHANGED, &CVideoDlg::OnShowModeChanged) - ON_MESSAGE(WM_SHOWBIG, &CVideoDlg::OnShowBig) - - ON_MESSAGE(WM_WINDOWSHARE, &CVideoDlg::OnWindowShareStart) - ON_MESSAGE(WM_DESKTOPSHARE, &CVideoDlg::OnDesktopShareStart) - - ON_MESSAGE(WM_MSGID(EID_JOINCHANNEL_SUCCESS), &CVideoDlg::OnEIDJoinChannelSuccess) - ON_MESSAGE(WM_MSGID(EID_REJOINCHANNEL_SUCCESS), &CVideoDlg::OnEIDReJoinChannelSuccess) - ON_MESSAGE(WM_MSGID(EID_FIRST_LOCAL_VIDEO_FRAME), &CVideoDlg::OnEIDFirstLocalFrame) - - ON_MESSAGE(WM_MSGID(EID_FIRST_REMOTE_VIDEO_DECODED), &CVideoDlg::OnEIDFirstRemoteFrameDecoded) - ON_MESSAGE(WM_MSGID(EID_USER_OFFLINE), &CVideoDlg::OnEIDUserOffline) - - ON_MESSAGE(WM_MSGID(EID_REMOTE_VIDEO_STAT), &CVideoDlg::OnRemoteVideoStat) - - ON_MESSAGE(WM_MSGID(EID_START_RCDSRV), &CVideoDlg::OnStartRecordingService) - ON_MESSAGE(WM_MSGID(EID_STOP_RCDSRV), &CVideoDlg::OnStopRecordingService) - - ON_MESSAGE(WM_MSGID(EID_STREAM_MESSAGE), &CVideoDlg::OnStreamMessage) - - - ON_BN_CLICKED(IDC_BTNMIN_VIDEO, &CVideoDlg::OnBnClickedBtnmin) - ON_BN_CLICKED(IDC_BTNCLOSE_VIDEO, &CVideoDlg::OnBnClickedBtnclose) - ON_BN_CLICKED(IDC_BTNRSTO_VIDEO, &CVideoDlg::OnBnClickedBtnrest) - ON_BN_CLICKED(IDC_BTNENDCALL_VIDEO, &CVideoDlg::OnBnClickedBtnclose) - - ON_BN_CLICKED(IDC_BTNMESSAGE_VIDEO, &CVideoDlg::OnBnClickedBtnmessage) - - ON_BN_CLICKED(IDC_BTNSCRCAP_VIDEO, &CVideoDlg::OnBnClickedBtnScreenCapture) - ON_BN_CLICKED(IDC_BTNMORE_VIDEO, &CVideoDlg::OnBnClickedBtnMore) - ON_BN_CLICKED(IDC_BTNMODE_VIDEO, &CVideoDlg::OnBnClickedBtnmode) - ON_BN_CLICKED(IDC_BTNAUDIO_VIDEO, &CVideoDlg::OnBnClickedBtnaudio) - - ON_BN_CLICKED(ID_IDR_VIDEOINFO, &CVideoDlg::OnBnClickedBtntip) - ON_BN_CLICKED(ID_IDR_DEVICE, &CVideoDlg::OnBnClickedBtnsetup) - ON_BN_CLICKED(ID_IDR_FILTER, &CVideoDlg::OnBnClickedBtnfilter) - -// ON_BN_CLICKED(IDC_BTNWHITEBOARD_VIDEO, &CVideoDlg::OnBnCliekedBtnWhiteBoard) -// ON_BN_CLICKED(IDC_BTNCLOSEWB_VIDEO, &CVideoDlg::OnBnCliekedBtnCloseWhiteBoard) - - ON_BN_CLICKED(IDC_BTNSCR_VIDEO, &CVideoDlg::OnBnClickedBtnfullscr) - - ON_BN_CLICKED(ID_SCRSHARE_DESKTOPSHARE, &CVideoDlg::OnBnClickedScreenshare) - ON_BN_CLICKED(ID_SCRSHARE_WINDOWSHARE, &CVideoDlg::OnBnClickedWindowshare) - -// ON_BN_CLICKED(ID_WHITEBOARD_HOSTMODE, &CVideoDlg::OnBnClickedHostMode) -// ON_BN_CLICKED(ID_WHITEBOARD_GUESTMODE, &CVideoDlg::OnBnClickedGuestMode) - ON_WM_SHOWWINDOW() - ON_WM_MOVE() -END_MESSAGE_MAP() - - -// CVideoDlg - - -void CVideoDlg::OnSize(UINT nType, int cx, int cy) -{ - CDialogEx::OnSize(nType, cx, cy); - - if (m_btnMin.GetSafeHwnd() != NULL) - m_btnMin.MoveWindow(cx - 72, 0, 24, 24, TRUE); - if (m_btnRst.GetSafeHwnd() != NULL) - m_btnRst.MoveWindow(cx - 48, 0, 24, 24, TRUE); - if (m_btnClose.GetSafeHwnd() != NULL) - m_btnClose.MoveWindow(cx - 24, 0, 24, 24, TRUE); - - GetClientRect(&m_rcVideoArea); - m_rcVideoArea.top += 24; - m_rcVideoArea.bottom -= 72; - - m_rcChildVideoArea.top = m_rcVideoArea.top + 10; - m_rcChildVideoArea.bottom = m_rcChildVideoArea.top + 144; - m_rcChildVideoArea.right = m_rcVideoArea.right - 14; - m_rcChildVideoArea.left = m_rcChildVideoArea.right - 192; - - if (::IsWindow(m_dlgChat.GetSafeHwnd()) && m_dlgChat.IsWindowVisible()) { - CRect rcChatArea; - - rcChatArea.CopyRect(&m_rcVideoArea); - rcChatArea.top = rcChatArea.bottom - 150; - ClientToScreen(&rcChatArea); - m_dlgChat.MoveWindow(&rcChatArea); - } - - if (m_wndLocal.GetSafeHwnd() == NULL || m_wndVideo[0].GetSafeHwnd() == NULL) - return; - - switch (m_nScreenMode) - { - case SCREEN_VIDEO1: - AdjustSizeVideo1(cx, cy); - AdjustButtonsNormal(cx, cy); - break; - case SCREEN_VIDEO4: - AdjustSizeVideo4(cx, cy); - AdjustButtonsNormal(cx, cy); - break; - case SCREEN_VIDEOMULTI: - AdjustSizeVideoMulti(cx, cy); - AdjustButtonsNormal(cx, cy); - break; - default: - break; - } - - Invalidate(TRUE); -} - -void CVideoDlg::ShowButtonsNormal() -{ - CRect rcClient; - int nShowMode = SW_HIDE; - - if (!m_bFullScreen) - nShowMode = SW_SHOW; - - m_btnMessage.ShowWindow(nShowMode); - m_btnMode.ShowWindow(nShowMode); - m_btnMore.ShowWindow(nShowMode); - - m_btnAudio.SetBackImage(IDB_BTNMAUDIO_VIDEO, RGB(0x26, 0x26, 0x26)); - m_btnAudio.ShowWindow(nShowMode); - m_btnEndCall.SetBackImage(IDB_BTNENDCALL_VIDEO, RGB(0x26, 0x26, 0x26)); - m_btnEndCall.ShowWindow(nShowMode); - m_btnScrCap.ShowWindow(nShowMode); - m_btnShow.ShowWindow(nShowMode); - - GetClientRect(&rcClient); - AdjustButtonsNormal(rcClient.Width(), rcClient.Height()); -} - - -void CVideoDlg::AdjustButtonsNormal(int cx, int cy) -{ -// if (m_btnSetup.GetSafeHwnd() != NULL) -// m_btnSetup.MoveWindow(30, cy - 48, 24, 24, TRUE); - - if(m_btnMessage.GetSafeHwnd() != NULL) - m_btnMessage.MoveWindow(cx / 2 - 312, cy - 60, 48, 48, TRUE); - if (m_btnMode.GetSafeHwnd() != NULL) - m_btnMode.MoveWindow(cx / 2 - 216, cy - 60, 48, 48, TRUE); - if (m_btnAudio.GetSafeHwnd() != NULL) - m_btnAudio.MoveWindow(cx / 2 - 120, cy - 60, 48, 48, TRUE); - if (m_btnEndCall.GetSafeHwnd() != NULL) - m_btnEndCall.MoveWindow(cx / 2 - 24, cy - 60, 48, 48, TRUE); - - if (m_btnScrCap.GetSafeHwnd() != NULL) - m_btnScrCap.MoveWindow(cx / 2 + 72, cy - 60, 48, 48, TRUE); - if (m_btnMore.GetSafeHwnd() != NULL) - m_btnMore.MoveWindow(cx / 2 + 264, cy - 60, 48, 48, TRUE); - - if (m_btnShow.GetSafeHwnd() != NULL) - m_btnShow.MoveWindow(cx - 72, cy - 48, 48, 48, TRUE); -} - -void CVideoDlg::AdjustSizeVideo1(int cx, int cy) -{ - if (m_listWndInfo.GetCount() == 0) - m_wndLocal.MoveWindow(&m_rcVideoArea, FALSE); - else { - m_wndVideo[0].MoveWindow(&m_rcVideoArea, FALSE); - m_wndLocal.MoveWindow(&m_rcChildVideoArea, FALSE); - } -} - -void CVideoDlg::AdjustSizeVideo4(int cx, int cy) -{ - m_wndVideo[0].MoveWindow(0, m_rcVideoArea.top, m_rcVideoArea.Width() / 2, m_rcVideoArea.Height() / 2, FALSE); - m_wndVideo[1].MoveWindow(m_rcVideoArea.Width() / 2, m_rcVideoArea.top, m_rcVideoArea.Width() / 2, m_rcVideoArea.Height() / 2, FALSE); - m_wndVideo[2].MoveWindow(0, m_rcVideoArea.top + m_rcVideoArea.Height() / 2, m_rcVideoArea.Width() / 2, m_rcVideoArea.Height() / 2, FALSE); - m_wndVideo[3].MoveWindow(m_rcVideoArea.Width() / 2, m_rcVideoArea.top + m_rcVideoArea.Height() / 2, m_rcVideoArea.Width() / 2, m_rcVideoArea.Height() / 2, FALSE); - - if (m_listWndInfo.GetCount() == 2) - m_wndLocal.MoveWindow(0, m_rcVideoArea.top + m_rcVideoArea.Height() / 2, m_rcVideoArea.Width() / 2, m_rcVideoArea.Height() / 2, FALSE); - else - m_wndLocal.MoveWindow(m_rcVideoArea.Width() / 2, m_rcVideoArea.top + m_rcVideoArea.Height() / 2, m_rcVideoArea.Width() / 2, m_rcVideoArea.Height() / 2, FALSE); -} - -void CVideoDlg::AdjustSizeVideoMulti(int cx, int cy) -{ - int nLocalIndex = 0; - - m_lpBigShowed->MoveWindow(&m_rcVideoArea, TRUE); - - for (int nIndex = 0; nIndex < 4; nIndex++) { - int nXPos = (m_rcVideoArea.Width() / 2) - 402 + (204 * nLocalIndex); - int nYPos = m_rcVideoArea.top + 16; - - if (!m_wndVideo[nIndex].IsBigShow()) { - if (m_wndVideo[nIndex].GetUID() != 0) { - m_wndVideo[nIndex].MoveWindow(nXPos, nYPos, 192, 144, TRUE); - nLocalIndex++; - } - } - else{ - m_wndLocal.MoveWindow(nXPos, nYPos, 192, 144, TRUE); - nLocalIndex++; - } - } -} - -void CVideoDlg::OnMouseMove(UINT nFlags, CPoint point) -{ - CDialogEx::OnMouseMove(nFlags, point); -} - -BOOL CVideoDlg::NeedShowSizeBox(CPoint point) -{ - CRect rcClient; - - GetClientRect(&rcClient); - - rcClient.left += 5; - rcClient.right -= 5; - rcClient.top += 5; - rcClient.bottom -= 5; - - if (rcClient.PtInRect(point) || IsZoomed()) - return FALSE; - - return TRUE; -} - -void CVideoDlg::EnableSize(BOOL bEnable) -{ - LONG lStyle = ::GetWindowLong(GetSafeHwnd(), GWL_STYLE); - - if (bEnable) - ::SetWindowLong(GetSafeHwnd(), GWL_STYLE, lStyle | WS_SIZEBOX); - else - ::SetWindowLong(GetSafeHwnd(), GWL_STYLE, lStyle&(~WS_SIZEBOX)); - - CRect rcClient; - - if (bEnable) - GetWindowRect(&rcClient); - else - GetClientRect(&rcClient); - - int cx = rcClient.Width(); - int cy = rcClient.Height(); - - if (m_bLastStat != bEnable) { - m_bLastStat = bEnable; - if (m_btnMin.GetSafeHwnd() != NULL) - m_btnMin.MoveWindow(cx - 72, 0, 24, 24, TRUE); - if (m_btnRst.GetSafeHwnd() != NULL) - m_btnRst.MoveWindow(cx - 48, 0, 24, 24, TRUE); - if (m_btnClose.GetSafeHwnd() != NULL) - m_btnClose.MoveWindow(cx - 24, 0, 24, 24, TRUE); - -// if (m_btnTip.GetSafeHwnd() != NULL) -// m_btnTip.MoveWindow(cx / 2 - 372, cy - 84, 72, 72, TRUE); - - if (m_btnScrCap.GetSafeHwnd() != NULL) - m_btnScrCap.MoveWindow(48, cy - 84, 48, 48, TRUE); - -// if (m_btnSetup.GetSafeHwnd() != NULL) -// m_btnSetup.MoveWindow(cx / 2 - 216, cy - 84, 72, 72, TRUE); - if (m_btnMode.GetSafeHwnd() != NULL) - m_btnMode.MoveWindow(cx / 2 - 96, cy - 84, 48, 48, TRUE); - if (m_btnAudio.GetSafeHwnd() != NULL) - m_btnAudio.MoveWindow(cx / 2 + 24, cy - 84, 48, 48, TRUE); - if (m_btnShow.GetSafeHwnd() != NULL) - m_btnShow.MoveWindow(cx - 72, cy - 84, 48, 48, TRUE); - if (m_btnEndCall.GetSafeHwnd() != NULL) - m_btnEndCall.MoveWindow(cx - 120, cy - 84, 48, 48, TRUE); - - Invalidate(FALSE); - } -} - -void CVideoDlg::OnPaint() -{ - CPaintDC dc(this); // device context for painting - //CDialogEx::OnPaint() - DrawHead(&dc); -} - - -LRESULT CVideoDlg::OnNcHitTest(CPoint point) -{ - LRESULT lResult = CDialogEx::OnNcHitTest(point); - if (lResult == HTCLIENT && ::GetAsyncKeyState(MK_LBUTTON) < 0) - lResult = HTCAPTION; - - return lResult; -} - -void CVideoDlg::OnBnClickedBtnmin() -{ - ShowWindow(SW_MINIMIZE); -} - -void CVideoDlg::OnBnClickedBtnclose() -{ - GetParent()->SendMessage(WM_LEAVECHANNEL, 0, 0); - - m_listWndInfo.RemoveAll(); - m_dlgChat.ShowWindow(SW_HIDE); - m_dlgDevice.ShowWindow(SW_HIDE); - - // unmute local video - CAgoraObject::GetAgoraObject()->MuteLocalVideo(FALSE); - m_btnMode.SetBackImage(IDB_BTNAUDIO_VIDEO); - - // unmute local audio - CAgoraObject::GetAgoraObject()->MuteLocalAudio(FALSE); - m_btnAudio.SwitchButtonStatus(CAGButton::AGBTN_NORMAL); - - CAgoraObject::GetAgoraObject()->EnableScreenCapture(NULL, 0, NULL, FALSE); - m_btnScrCap.SwitchButtonStatus(CAGButton::AGBTN_NORMAL); - - m_dlgChat.ShowWindow(SW_HIDE); - m_dlgChat.ClearHistory(); - m_btnMessage.SwitchButtonStatus(CAGButton::AGBTN_NORMAL); - - CDialogEx::OnOK(); -} - -void CVideoDlg::OnBnClickedBtnrest() -{ - if (IsZoomed()) { - m_btnRst.SetBackImage(IDB_BTNMAX, RGB(0xFF, 0x00, 0xFF)); - ShowWindow(SW_RESTORE); - } - else{ - m_btnRst.SetBackImage(IDB_BTNRESTORE, RGB(0xFF, 0x00, 0xFF)); - ShowWindow(SW_MAXIMIZE); - } - - CRect rcClient; - - GetClientRect(&rcClient); - m_rcVideoArea.CopyRect(&rcClient); - m_rcVideoArea.top += 24; - m_rcVideoArea.bottom -= 72; - - m_rcChildVideoArea.top = m_rcVideoArea.top + 16; - m_rcChildVideoArea.bottom = m_rcChildVideoArea.top + 144; - m_rcChildVideoArea.left = m_rcVideoArea.right - 212; - m_rcChildVideoArea.right = m_rcVideoArea.right - 20; - - int cx = rcClient.Width(); - int cy = rcClient.Height(); - - switch (m_nScreenMode) - { - case SCREEN_VIDEO1: - AdjustSizeVideo1(cx, cy); - AdjustButtonsNormal(cx, cy); - break; - case SCREEN_VIDEO4: - AdjustSizeVideo4(cx, cy); - AdjustButtonsNormal(cx, cy); - break; - case SCREEN_VIDEOMULTI: - AdjustSizeVideoMulti(cx, cy); - AdjustButtonsNormal(cx, cy); - break; - default: - break; - } - - Invalidate(TRUE); -} - - -void CVideoDlg::OnBnClickedBtnfullscr() -{ - int nShowMode = 0; - - if (m_bFullScreen) { - m_bFullScreen = FALSE; - nShowMode = SW_SHOW; - ShowWindow(SW_RESTORE); - - GetClientRect(&m_rcVideoArea); - m_rcVideoArea.top += 24; - m_rcVideoArea.bottom -= 72; - } - else{ - m_bFullScreen = TRUE; - nShowMode = SW_HIDE; - ShowWindow(SW_MAXIMIZE); - - GetClientRect(&m_rcVideoArea); - } - - m_btnMin.ShowWindow(nShowMode); - m_btnRst.ShowWindow(nShowMode); - m_btnClose.ShowWindow(nShowMode); - - m_btnMessage.ShowWindow(nShowMode); - m_btnMode.ShowWindow(nShowMode); - m_btnAudio.ShowWindow(nShowMode); - m_btnEndCall.ShowWindow(nShowMode); - m_btnScrCap.ShowWindow(nShowMode); - m_btnMore.ShowWindow(nShowMode); - - m_btnShow.ShowWindow(nShowMode); - - switch (m_nScreenMode) - { - case SCREEN_VIDEO1: - ShowVideo1(); - break; - case SCREEN_VIDEO4: - ShowVideo4(); - break; - case SCREEN_VIDEOMULTI: - ShowMulti(); - break; - default: - break; - } - - Invalidate(TRUE); -} - -void CVideoDlg::OnBnClickedScreenshare() -{ - m_dlgDesktopCapture.SaveScreen(NULL); - m_dlgDesktopCapture.ShowWindow(SW_MAXIMIZE); -} - -void CVideoDlg::OnBnClickedWindowshare() -{ - m_dlgScreenCapture.RefreashWndInfo(); - m_dlgScreenCapture.SaveScreen(NULL); - - m_dlgScreenCapture.ShowWindow(SW_MAXIMIZE); -} - -void CVideoDlg::ShowControlButton(BOOL bShow) -{ - int nShowMode = 0; - if (bShow) - nShowMode = SW_SHOW; - else - nShowMode = SW_HIDE; - - m_btnScrCap.ShowWindow(nShowMode); - m_btnMessage.ShowWindow(nShowMode); - m_btnMode.ShowWindow(nShowMode); - m_btnMore.ShowWindow(nShowMode); - m_btnAudio.ShowWindow(nShowMode); - m_btnShow.ShowWindow(nShowMode); - m_btnEndCall.ShowWindow(nShowMode); -} - -void CVideoDlg::OnBnClickedBtntip() -{ - for (int nIndex = 0; nIndex < 4; nIndex++) - m_wndVideo[nIndex].ShowVideoInfo(!m_bShowInfo); - - m_bShowInfo = !m_bShowInfo; -} - -void CVideoDlg::OnBnClickedBtnScreenCapture() -{ - CAgoraObject *lpAgora = CAgoraObject::GetAgoraObject(); - - if (lpAgora->IsScreenCaptureEnabled()) { - lpAgora->EnableScreenCapture(NULL, 0, NULL, FALSE); - m_btnScrCap.SwitchButtonStatus(CAGButton::AGBTN_NORMAL); - CAgoraObject::GetAgoraObject()->EnableLocalRender(TRUE); - } - else - CreateScreenShareMenu(); - - Invalidate(); -} - -void CVideoDlg::OnBnClickedBtnMore() -{ - CreateMoreMenu(); -} - -void CVideoDlg::CreateScreenShareMenu() -{ - CRect rcButton; - CMenu Menu; - MENUITEMINFO mii; - - Menu.LoadMenu(IDR_MENU_SCRSHARE); - - CMenu *pMenuPopup = Menu.GetSubMenu(0); - - mii.cbSize = sizeof(MENUITEMINFO); - mii.fMask = MIIM_STRING; - - mii.dwTypeData = const_castLANG_STR("IDS_VIDEO_SCRSHARE"); - mii.cch = _tcslen(LANG_STR("IDS_VIDEO_SCRSHARE")) + 1; - pMenuPopup->SetMenuItemInfo(0, &mii, FALSE); - - mii.dwTypeData = const_castLANG_STR("IDS_VIDEO_WNDSHARE"); - mii.cch = _tcslen(LANG_STR("IDS_VIDEO_WNDSHARE")) + 1; - pMenuPopup->SetMenuItemInfo(1, &mii, FALSE); - m_btnScrCap.GetWindowRect(&rcButton); - - int x = rcButton.left - 60; - int y = rcButton.top - 50; - - pMenuPopup->TrackPopupMenu(TPM_RIGHTBUTTON, x, y, this); - pMenuPopup->DestroyMenu(); -} - - -void CVideoDlg::CreateMoreMenu() -{ - CRect rcButton; - CMenu Menu; - MENUITEMINFO mii; - UINT nFlag = 0; - - Menu.LoadMenu(IDR_MENU_MORE); - - CMenu *pMenuPopup = Menu.GetSubMenu(0); - - mii.cbSize = sizeof(MENUITEMINFO); - mii.fMask = MIIM_STRING; - - mii.dwTypeData = const_castLANG_STR("IDS_VIDEO_MOREINFO"); - mii.cch = _tcslen(LANG_STR("IDS_VIDEO_MOREINFO")) + 1; - pMenuPopup->SetMenuItemInfo(0, &mii, FALSE); - pMenuPopup->SetMenuItemBitmaps(ID_IDR_VIDEOINFO, MF_BYCOMMAND, &m_bitMenuInfo, &m_bitMenuInfo); - if (m_bShowInfo) - nFlag = MF_BYCOMMAND | MF_CHECKED; - else - nFlag = MF_BYCOMMAND | MF_UNCHECKED; - pMenuPopup->CheckMenuItem(ID_IDR_VIDEOINFO, nFlag); - - mii.dwTypeData = const_castLANG_STR("IDS_VIDEO_MOREDEVICE"); - mii.cch = _tcslen(LANG_STR("IDS_VIDEO_MOREDEVICE")) + 1; - pMenuPopup->SetMenuItemInfo(1, &mii, FALSE); - pMenuPopup->SetMenuItemBitmaps(ID_IDR_DEVICE, MF_BYCOMMAND, &m_bitMenuDevice, &m_bitMenuDevice); - - mii.dwTypeData = const_castLANG_STR("IDS_VIDEO_MOREFILTER"); - mii.cch = _tcslen(LANG_STR("IDS_VIDEO_MOREFILTER")) + 1; - pMenuPopup->SetMenuItemInfo(2, &mii, FALSE); - pMenuPopup->SetMenuItemBitmaps(ID_IDR_FILTER, MF_BYCOMMAND, &m_bitMenuFilter, &m_bitMenuFilter); - if (m_bFilter) - nFlag = MF_BYCOMMAND | MF_CHECKED; - else - nFlag = MF_BYCOMMAND | MF_UNCHECKED; - pMenuPopup->CheckMenuItem(ID_IDR_FILTER, nFlag); - - - m_btnMore.GetWindowRect(&rcButton); - - int x = rcButton.left - 60; - int y = rcButton.top - 75; - - pMenuPopup->TrackPopupMenu(TPM_RIGHTBUTTON, x, y, this); - pMenuPopup->DestroyMenu(); -} - -void CVideoDlg::OnBnClickedBtnsetup() -{ - m_dlgDevice.ShowWindow(SW_SHOW); - m_dlgDevice.CenterWindow(); -} - -void CVideoDlg::OnBnClickedBtnfilter() -{ - IRtcEngine *lpEngine = CAgoraObject::GetEngine(); - - if (!m_bFilter){ - load_preprocessing_plugin(lpEngine); - } - else{ - unload_preprocessing_plugin(lpEngine); - } - - m_bFilter = !m_bFilter; -} - -void CVideoDlg::OnBnClickedBtnmessage() -{ - BOOL bIsShowing = m_dlgChat.IsWindowVisible(); - CRect rcChatArea; - - rcChatArea.CopyRect(&m_rcVideoArea); - rcChatArea.top = rcChatArea.bottom - 150; - ClientToScreen(&rcChatArea); - - if (bIsShowing) { - m_dlgChat.ShowWindow(SW_HIDE); - m_btnMessage.SwitchButtonStatus(CAGButton::AGBTN_NORMAL); - } - else { - m_dlgChat.ShowWindow(SW_SHOW); - m_dlgChat.MoveWindow(&rcChatArea, TRUE); - m_btnMessage.SwitchButtonStatus(CAGButton::AGBTN_PUSH); - } -} - -void CVideoDlg::OnBnClickedBtnmode() -{ - CAgoraObject *lpAgora = CAgoraObject::GetAgoraObject(); - IRtcEngine *lpRtcEngine = CAgoraObject::GetEngine(); - - if (!lpAgora->IsLocalVideoMuted()) { - lpAgora->MuteLocalVideo(TRUE); - m_btnMode.SetBackImage(IDB_BTNVIDEO_VIDEO); - - CAgoraObject::GetAgoraObject()->EnableLocalRender(FALSE); - m_wndLocal.SetBackImage(IDB_BACKGROUND_VIDEO, 96, 96); - m_wndLocal.ShowBackground(TRUE); - } - else { - lpAgora->EnableVideo(TRUE); - lpAgora->MuteLocalVideo(FALSE); - CAgoraObject::GetAgoraObject()->EnableLocalRender(TRUE); - m_btnMode.SetBackImage(IDB_BTNAUDIO_VIDEO); - m_wndLocal.ShowBackground(FALSE); - } - - m_wndLocal.Invalidate(TRUE); - m_wndLocal.UpdateWindow(); - - Invalidate(TRUE); - UpdateWindow(); -} - -void CVideoDlg::OnBnClickedBtnaudio() -{ - CAgoraObject *lpAgora = CAgoraObject::GetAgoraObject(); - - if (lpAgora->IsLocalAudioMuted()) { - lpAgora->MuteLocalAudio(FALSE); - m_btnAudio.SwitchButtonStatus(CAGButton::AGBTN_NORMAL); - } - else { - lpAgora->MuteLocalAudio(TRUE); - m_btnAudio.SwitchButtonStatus(CAGButton::AGBTN_PUSH); - } -} - -LRESULT CVideoDlg::OnEIDJoinChannelSuccess(WPARAM wParam, LPARAM lParam) -{ - LPAGE_JOINCHANNEL_SUCCESS lpData = (LPAGE_JOINCHANNEL_SUCCESS)wParam; - - m_listWndInfo.RemoveAll(); - CAgoraObject::GetAgoraObject()->SetSelfUID(lpData->uid); - - delete lpData; - return 0; -} - -LRESULT CVideoDlg::OnEIDReJoinChannelSuccess(WPARAM wParam, LPARAM lParam) -{ - LPAGE_REJOINCHANNEL_SUCCESS lpData = (LPAGE_REJOINCHANNEL_SUCCESS)wParam; - - m_listWndInfo.RemoveAll(); - delete lpData; - - return 0; -} - -LRESULT CVideoDlg::OnEIDFirstLocalFrame(WPARAM wParam, LPARAM lParam) -{ - LPAGE_FIRST_LOCAL_VIDEO_FRAME lpData = (LPAGE_FIRST_LOCAL_VIDEO_FRAME)wParam; - - if (m_listWndInfo.GetCount() == 0) - ShowVideo1(); - - delete lpData; - - return 0; -} - -LRESULT CVideoDlg::OnEIDFirstRemoteFrameDecoded(WPARAM wParam, LPARAM lParam) -{ - LPAGE_FIRST_REMOTE_VIDEO_DECODED lpData = (LPAGE_FIRST_REMOTE_VIDEO_DECODED)wParam; - BOOL bFound = FALSE; - - POSITION pos = m_listWndInfo.GetHeadPosition(); - while (pos != NULL) { - AGVIDEO_WNDINFO &agvWndInfo = m_listWndInfo.GetNext(pos); - if (agvWndInfo.nUID == lpData->uid) { - bFound = TRUE; - break; - } - } - - if (!bFound) { - AGVIDEO_WNDINFO agvWndInfo; - memset(&agvWndInfo, 0, sizeof(AGVIDEO_WNDINFO)); - agvWndInfo.nUID = lpData->uid; - agvWndInfo.nWidth = lpData->width; - agvWndInfo.nHeight = lpData->height; - - m_listWndInfo.AddTail(agvWndInfo); - } - - RebindVideoWnd(); - - delete lpData; - - return 0; -} - -LRESULT CVideoDlg::OnEIDUserJoined(WPARAM wParam, LPARAM lParam) -{ - CString str; - LPAGE_USER_JOINED lpData = (LPAGE_USER_JOINED)wParam; - - str.Format(_T("%d joined the channel"), lpData->uid); - MessageBox(str); - return 0; -} - -LRESULT CVideoDlg::OnEIDUserOffline(WPARAM wParam, LPARAM lParam) -{ - LPAGE_USER_OFFLINE lpData = (LPAGE_USER_OFFLINE)wParam; - - POSITION pos = m_listWndInfo.GetHeadPosition(); - while (pos != NULL){ - if (m_listWndInfo.GetAt(pos).nUID == lpData->uid) { - m_listWndInfo.RemoveAt(pos); - RebindVideoWnd(); - break; - } - - m_listWndInfo.GetNext(pos); - } - - delete lpData; - - return 0; -} - -LRESULT CVideoDlg::OnEIDConnectionLost(WPARAM wParam, LPARAM lParam) -{ - return 0; -} - -LRESULT CVideoDlg::OnEIDVideoDeviceChanged(WPARAM wParam, LPARAM lParam) -{ - return 0; -} - -LRESULT CVideoDlg::OnRemoteVideoStat(WPARAM wParam, LPARAM lParam) -{ - LPAGE_REMOTE_VIDEO_STAT lpData = (LPAGE_REMOTE_VIDEO_STAT)wParam; - - POSITION posNext = m_listWndInfo.GetHeadPosition(); - - while (posNext != NULL) { - AGVIDEO_WNDINFO &rWndInfo = m_listWndInfo.GetNext(posNext); - - if (rWndInfo.nUID == lpData->uid) { - rWndInfo.nFramerate = lpData->rendererOutputFrameRate; - rWndInfo.nBitrate = lpData->receivedBitrate; - rWndInfo.nWidth = lpData->width; - rWndInfo.nHeight = lpData->height; - m_wndVideo[rWndInfo.nIndex].SetFrameRateInfo(rWndInfo.nFramerate); - m_wndVideo[rWndInfo.nIndex].SetBitrateInfo(rWndInfo.nBitrate); - m_wndVideo[rWndInfo.nIndex].SetVideoResolution(rWndInfo.nWidth, rWndInfo.nHeight); - break; - } - } - - delete lpData; - - return 0; -} - -LRESULT CVideoDlg::OnStartRecordingService(WPARAM wParam, LPARAM lParam) -{ - - return 0; -} - -LRESULT CVideoDlg::OnStopRecordingService(WPARAM wParam, LPARAM lParam) -{ - return 0; -} - -LRESULT CVideoDlg::OnStreamMessage(WPARAM wParam, LPARAM lParam) -{ - LPAGE_STREAM_MESSAGE lpData = (LPAGE_STREAM_MESSAGE)wParam; - TCHAR szMessage[256]; - - int nUTF8Len = lpData->length; - - memset(szMessage, 0, 256 * sizeof(TCHAR)); -#ifdef UNICODE - ::MultiByteToWideChar(CP_UTF8, 0, lpData->data, lpData->length, szMessage, 256); -#else - _tcscpy_s(szMessage, 256, lpData->data); -#endif - - m_dlgChat.AddChatMessage(lpData->uid, szMessage); - - delete[] lpData->data; - delete lpData; - - return 0; -} - -void CVideoDlg::DrawHead(CDC *pDC) -{ - CRect rcTitle; - CString strTitle; - - if (m_bFullScreen) - return; - - GetWindowText(strTitle); - GetClientRect(&rcTitle); - CBrush *lpDefaultBrush = pDC->SelectObject(&m_brHead); - - rcTitle.bottom = 24; - pDC->FillRect(&rcTitle, &m_brHead); - - pDC->SetBkMode(TRANSPARENT); - pDC->SetTextColor(RGB(0xFF, 0xFF, 0xFF)); - pDC->DrawText(strTitle, &rcTitle, DT_SINGLELINE | DT_VCENTER | DT_CENTER); - pDC->SelectObject(lpDefaultBrush); -} - -void CVideoDlg::InitCtrls() -{ - CRect rcClient; - int nScreenWidth = ::GetSystemMetrics(SM_CXSCREEN); - int nScreenHeight = ::GetSystemMetrics(SM_CYSCREEN); - - GetClientRect(&rcClient); - - m_btnMessage.Create(NULL, WS_VISIBLE | WS_CHILD, CRect(0, 0, 1, 1), this, IDC_BTNMESSAGE_VIDEO); - m_btnMode.Create(NULL, WS_VISIBLE | WS_CHILD, CRect(0, 0, 1, 1), this, IDC_BTNMODE_VIDEO); - m_btnAudio.Create(NULL, WS_VISIBLE | WS_CHILD, CRect(0, 0, 1, 1), this, IDC_BTNAUDIO_VIDEO); - m_btnEndCall.Create(NULL, WS_VISIBLE | WS_CHILD, CRect(0, 0, 1, 1), this, IDC_BTNENDCALL_VIDEO); - m_btnScrCap.Create(NULL, WS_VISIBLE | WS_CHILD, CRect(0, 0, 1, 1), this, IDC_BTNSCRCAP_VIDEO); - m_btnMore.Create(NULL, WS_VISIBLE | WS_CHILD, CRect(0, 0, 1, 1), this, IDC_BTNMORE_VIDEO); - - m_btnShow.Create(NULL, WS_VISIBLE | WS_CHILD, CRect(0, 0, 1, 1), this, IDC_BTNSCR_VIDEO); - - for (int nIndex = 0; nIndex < 4; nIndex++){ - m_wndVideo[nIndex].Create(NULL, NULL, WS_CHILD | WS_VISIBLE | WS_BORDER, CRect(0, 0, 1, 1), this, IDC_BASEWND_VIDEO + nIndex); - m_wndVideo[nIndex].SetBackImage(IDB_BACKGROUND_VIDEO, 96, 96, RGB(0x44, 0x44, 0x44)); - m_wndVideo[nIndex].SetFaceColor(RGB(0x58, 0x58, 0x58)); - } - - m_wndLocal.Create(NULL, NULL, WS_CHILD | WS_VISIBLE | WS_BORDER, CRect(0, 0, 1, 1), this, IDC_BASEWND_VIDEO + 4); - m_wndLocal.SetBackImage(IDB_BACKGROUND_VIDEO, 96, 96, RGB(0x44, 0x44, 0x44)); - m_wndLocal.SetFaceColor(RGB(0x58, 0x58, 0x58)); - m_wndLocal.SetUID(0); - - m_btnMin.MoveWindow(rcClient.Width() - 72, 1, 22, 22, TRUE); - m_btnRst.MoveWindow(rcClient.Width() - 48, 1, 22, 22, TRUE); - m_btnClose.MoveWindow(rcClient.Width() - 24, 1, 22, 22, TRUE); - - m_btnMessage.MoveWindow(rcClient.Width() / 2 - 144, rcClient.Height() - 84, 48, 48, TRUE); - m_btnMode.MoveWindow(rcClient.Width() / 2 - 24, rcClient.Height() - 84, 48, 48, TRUE); - m_btnAudio.MoveWindow(rcClient.Width() / 2 + 24, rcClient.Height() - 84, 48, 48, TRUE); - m_btnShow.MoveWindow(rcClient.Width() - 72, rcClient.Height() - 84, 48, 48, TRUE); - m_btnMore.MoveWindow(rcClient.Width() / 2 + 264, rcClient.Height() - 84, 48, 48, TRUE); - m_btnEndCall.MoveWindow(rcClient.Width() - 120, rcClient.Height() - 84, 48, 48, TRUE); - - m_wndVideo[0].MoveWindow(0, 24, rcClient.Width(), rcClient.Height() - 96, TRUE); - - m_btnMin.SetBackImage(IDB_BTNMIN, RGB(0xFF, 0x00, 0xFF)); - m_btnRst.SetBackImage(IDB_BTNMAX, RGB(0xFF, 0x00, 0xFF)); - m_btnClose.SetBackImage(IDB_BTNCLOSE, RGB(0xFF, 0x00, 0xFF)); - - m_btnScrCap.SetBackColor(RGB(0x26, 0x26, 0x26), RGB(0x26, 0x26, 0x26), RGB(0x26, 0x26, 0x26), RGB(0x26, 0x26, 0x26)); - m_btnScrCap.EnableFrameEffect(FALSE); - m_btnScrCap.SetBackImage(IDB_BTNSCRCAP_VIDEO, RGB(0x26, 0x26, 0x26)); - - m_btnMessage.SetBackColor(RGB(0x26, 0x26, 0x26), RGB(0x26, 0x26, 0x26), RGB(0x26, 0x26, 0x26), RGB(0x26, 0x26, 0x26)); - m_btnMessage.EnableFrameEffect(FALSE); - m_btnMessage.SetBackImage(IDB_BTNMSG_VIDEO, RGB(0x26, 0x26, 0x26)); - - m_btnMode.SetBackColor(RGB(0x26, 0x26, 0x26), RGB(0x26, 0x26, 0x26), RGB(0x26, 0x26, 0x26), RGB(0x26, 0x26, 0x26)); - m_btnMode.EnableFrameEffect(FALSE); - m_btnMode.SetBackImage(IDB_BTNAUDIO_VIDEO, RGB(0x26, 0x26, 0x26)); - - m_btnAudio.SetBackColor(RGB(0x26, 0x26, 0x26), RGB(0x26, 0x26, 0x26), RGB(0x26, 0x26, 0x26), RGB(0x26, 0x26, 0x26)); - m_btnAudio.EnableFrameEffect(FALSE); - m_btnAudio.SetBackImage(IDB_BTNMAUDIO_VIDEO, RGB(0x26, 0x26, 0x26)); - - m_btnShow.SetBackColor(RGB(0x26, 0x26, 0x26), RGB(0x26, 0x26, 0x26), RGB(0x26, 0x26, 0x26), RGB(0x26, 0x26, 0x26)); - m_btnShow.EnableFrameEffect(FALSE); - m_btnShow.SetBackImage(IDB_BTNFULLSCR_VIDEO, RGB(0x26, 0x26, 0x26)); - - m_btnEndCall.SetBackColor(RGB(0x26, 0x26, 0x26), RGB(0x26, 0x26, 0x26), RGB(0x26, 0x26, 0x26), RGB(0x26, 0x26, 0x26)); - m_btnEndCall.EnableFrameEffect(FALSE); - m_btnEndCall.SetBackImage(IDB_BTNENDCALL_VIDEO, RGB(0x26, 0x26, 0x26)); - - m_btnMore.SetBackColor(RGB(0x26, 0x26, 0x26), RGB(0x26, 0x26, 0x26), RGB(0x26, 0x26, 0x26), RGB(0x26, 0x26, 0x26)); - m_btnMore.EnableFrameEffect(FALSE); - m_btnMore.SetBackImage(IDB_BTNMORE_VIDEO, RGB(0x26, 0x26, 0x26)); -} - -void CVideoDlg::ShowVideo1() -{ - m_wndLocal.ShowWindow(SW_HIDE); - m_wndLocal.SetBigShowFlag(FALSE); - for (int nIndex = 0; nIndex < 4; nIndex++) { - m_wndVideo[nIndex].ShowWindow(SW_HIDE); - m_wndVideo[nIndex].SetBigShowFlag(FALSE); - } - - if (m_listWndInfo.GetCount() == 0) { - m_wndLocal.MoveWindow(&m_rcVideoArea, FALSE); - m_wndLocal.SetParent(this); - m_wndLocal.SetBigShowFlag(TRUE); - m_wndLocal.ShowWindow(SW_SHOW); - } - else { - m_wndVideo[0].MoveWindow(&m_rcVideoArea, FALSE); - m_wndVideo[0].ShowWindow(SW_SHOW); - m_wndVideo[0].SetBigShowFlag(TRUE); - m_wndVideo[0].SetParent(this); - - m_wndLocal.MoveWindow(&m_rcChildVideoArea, FALSE); - m_wndLocal.SetParent(&m_wndVideo[0]); - m_wndLocal.ShowWindow(SW_SHOW); - m_wndLocal.SetParent(&m_wndVideo[0]); - } - - m_nScreenMode = SCREEN_VIDEO1; - - ShowButtonsNormal(); -} - -void CVideoDlg::ShowVideo4() -{ - m_wndLocal.ShowWindow(SW_HIDE); - m_wndLocal.SetBigShowFlag(FALSE); - for (int nIndex = 0; nIndex < 4; nIndex++) { - m_wndVideo[nIndex].ShowWindow(SW_SHOW); - m_wndVideo[nIndex].SetBigShowFlag(FALSE); - m_wndVideo[nIndex].SetParent(this); - } - - m_wndVideo[0].MoveWindow(0, m_rcVideoArea.top, m_rcVideoArea.Width() / 2, m_rcVideoArea.Height() / 2, FALSE); - m_wndVideo[1].MoveWindow(m_rcVideoArea.Width() / 2, m_rcVideoArea.top, m_rcVideoArea.Width() / 2, m_rcVideoArea.Height() / 2, FALSE); - m_wndVideo[2].MoveWindow(0, m_rcVideoArea.top + m_rcVideoArea.Height() / 2, m_rcVideoArea.Width() / 2, m_rcVideoArea.Height() / 2, FALSE); - m_wndVideo[3].MoveWindow(m_rcVideoArea.Width() / 2, m_rcVideoArea.top + m_rcVideoArea.Height() / 2, m_rcVideoArea.Width() / 2, m_rcVideoArea.Height() / 2, FALSE); - - CRect rcLocal; - int nRemoteCount = m_listWndInfo.GetCount(); - - if (nRemoteCount == 2) - m_wndLocal.MoveWindow(0, m_rcVideoArea.top + m_rcVideoArea.Height() / 2, m_rcVideoArea.Width() / 2, m_rcVideoArea.Height() / 2, FALSE); - else - m_wndLocal.MoveWindow(m_rcVideoArea.Width() / 2, m_rcVideoArea.top + m_rcVideoArea.Height() / 2, m_rcVideoArea.Width() / 2, m_rcVideoArea.Height() / 2, FALSE); - - m_wndVideo[nRemoteCount].ShowWindow(SW_HIDE); - m_wndLocal.SetParent(this); - m_wndLocal.ShowWindow(SW_SHOW); - - m_nScreenMode = SCREEN_VIDEO4; - - ShowButtonsNormal(); - -} - -void CVideoDlg::ShowMulti() -{ - int nLocalIndex = 0; - - m_wndLocal.ShowWindow(TRUE); - m_wndLocal.SetBigShowFlag(FALSE); - for (int nIndex = 0; nIndex < 4; nIndex++) { - m_wndVideo[nIndex].ShowWindow(SW_HIDE); - m_wndVideo[nIndex].SetBigShowFlag(FALSE); - } - - if (m_lpBigShowed == NULL) - m_lpBigShowed = &m_wndVideo[0]; - - m_lpBigShowed->ShowWindow(SW_SHOW); - m_lpBigShowed->MoveWindow(&m_rcVideoArea, TRUE); - m_lpBigShowed->SetParent(this); - m_lpBigShowed->SetBigShowFlag(TRUE); - - for (int nIndex = 0; nIndex < 4; nIndex++) { - int nXPos = (m_rcVideoArea.Width() / 2) - 402 + (204 * nLocalIndex); - int nYPos = m_rcVideoArea.top + 16; - - if (!m_wndVideo[nIndex].IsBigShow()) { - if (m_wndVideo[nIndex].GetUID() != 0) { - m_wndVideo[nIndex].MoveWindow(nXPos, nYPos, 192, 144, TRUE); - m_wndVideo[nIndex].ShowWindow(SW_SHOW); - m_wndVideo[nIndex].SetParent(m_lpBigShowed); - nLocalIndex++; - } - } - else{ - m_wndLocal.MoveWindow(nXPos, nYPos, 192, 144, TRUE); - m_wndLocal.ShowWindow(SW_SHOW); - m_wndLocal.SetParent(m_lpBigShowed); - nLocalIndex++; - } - } - - m_nScreenMode = SCREEN_VIDEOMULTI; - - ShowButtonsNormal(); -} - -BOOL CVideoDlg::OnInitDialog() -{ - CDialogEx::OnInitDialog(); - - m_dlgDevice.Create(CDeviceDlg::IDD, this); - m_dlgDevice.EnableDeviceTest(FALSE); - - m_dlgScreenCapture.Create(CAGScreenCaptureDlg::IDD, this); - m_dlgDesktopCapture.Create(CAGDesktopCaptureDlg::IDD, this); - m_dlgChat.Create(CChatDlg::IDD, this); - InitCtrls(); - - m_bitMenuInfo.LoadBitmap(IDB_MENU_INFO); - m_bitMenuDevice.LoadBitmap(IDB_MENU_DEVICE); - m_bitMenuFilter.LoadBitmap(IDB_MENU_FILTER); - - return TRUE; // return TRUE unless you set the focus to a control -} - - -HWND CVideoDlg::GetRemoteVideoWnd(int nIndex) -{ - if (nIndex < 0 || nIndex > 3) - return NULL; - - return m_wndVideo[nIndex].GetSafeHwnd(); -} - - -void CVideoDlg::RebindVideoWnd() -{ - if (m_wndVideo[0].GetSafeHwnd() == NULL || m_wndLocal.GetSafeHwnd() == NULL) - return; - - VideoCanvas canvas; - - canvas.renderMode = RENDER_MODE_FIT; - - POSITION pos = m_listWndInfo.GetHeadPosition(); - for (int nIndex = 0; nIndex < 4; nIndex++) { - if (pos != NULL) { - AGVIDEO_WNDINFO &agvWndInfo = m_listWndInfo.GetNext(pos); - canvas.uid = agvWndInfo.nUID; - canvas.view = m_wndVideo[nIndex].GetSafeHwnd(); - agvWndInfo.nIndex = nIndex; - - CAgoraObject::GetEngine()->setupRemoteVideo(canvas); - m_wndVideo[nIndex].SetUID(canvas.uid); - m_wndVideo[nIndex].SetVideoResolution(agvWndInfo.nWidth, agvWndInfo.nHeight); - m_wndVideo[nIndex].SetFrameRateInfo(agvWndInfo.nFramerate); - m_wndVideo[nIndex].SetBitrateInfo(agvWndInfo.nBitrate); - } - else - m_wndVideo[nIndex].SetUID(0); - } - - if (m_nScreenMode != SCREEN_VIDEOMULTI) { - if (m_listWndInfo.GetCount() <= 1) - ShowVideo1(); - else if (m_listWndInfo.GetCount() > 1 && m_listWndInfo.GetCount() < 4) - ShowVideo4(); - else - ShowMulti(); - } - else - ShowMulti(); -} - -BOOL CVideoDlg::PreTranslateMessage(MSG* pMsg) -{ - if (pMsg->message == WM_KEYDOWN){ - switch (pMsg->wParam){ - case VK_RETURN: - return FALSE; - case VK_ESCAPE: - if (m_bFullScreen) - OnBnClickedBtnfullscr(); - - return FALSE; - } - } - - return CDialogEx::PreTranslateMessage(pMsg); -} - -LRESULT CVideoDlg::OnShowModeChanged(WPARAM wParam, LPARAM lParam) -{ - if (m_nScreenMode == SCREEN_VIDEOMULTI) { - if (m_listWndInfo.GetCount() <= 1) - ShowVideo1(); - else if (m_listWndInfo.GetCount() > 1 && m_listWndInfo.GetCount() < 4) - ShowVideo4(); - } - else { - m_lpBigShowed = (CAGVideoWnd *)wParam; - ShowMulti(); - } - - return 0; -} - -LRESULT CVideoDlg::OnShowBig(WPARAM wParam, LPARAM lParam) -{ - CRect rcNextBig; - CRect rcCurBig; - - if (m_nScreenMode != SCREEN_VIDEOMULTI) - return 0; - - CAGVideoWnd *lpNextBigWnd = (CAGVideoWnd *)wParam; - if (lpNextBigWnd == m_lpBigShowed) - return 0; - - ShowMulti(); - m_lpBigShowed = lpNextBigWnd; - - return 0; -} - -LRESULT CVideoDlg::OnWindowShareStart(WPARAM wParam, LPARAM lParam) -{ - HWND hShareWnd = (HWND)wParam; - if (hShareWnd == GetSafeHwnd()) { - CAgoraObject::GetAgoraObject()->EnableLocalRender(FALSE); - m_wndLocal.Invalidate(TRUE); - } - - CAgoraObject::GetAgoraObject()->EnableScreenCapture((HWND)wParam, 15, NULL, TRUE); - m_btnScrCap.SwitchButtonStatus(CAGButton::AGBTN_PUSH); - - return 0; -} - -LRESULT CVideoDlg::OnDesktopShareStart(WPARAM wParam, LPARAM lParam) -{ - LPDESKTOP_SHARE_PARAM lpDesktopShareParam = (LPDESKTOP_SHARE_PARAM)(wParam); - CRect rcRegion; - - CAgoraObject::GetAgoraObject()->EnableVideo(); - - rcRegion.left = lpDesktopShareParam->nX; - rcRegion.top = lpDesktopShareParam->nY; - rcRegion.right = rcRegion.left + lpDesktopShareParam->nWidth; - rcRegion.bottom = rcRegion.top + lpDesktopShareParam->nHeight; - - CAgoraObject::GetAgoraObject()->EnableScreenCapture(NULL, lpDesktopShareParam->nFPS, &rcRegion, TRUE); - // Sleep(1000); - // CAgoraObject::GetAgoraObject()->SetVideoProfileEx(lpDesktopShareParam->nWidth, lpDesktopShareParam->nHeight, lpDesktopShareParam->nFPS, lpDesktopShareParam->nBitrate); - - m_btnScrCap.SwitchButtonStatus(CAGButton::AGBTN_PUSH); - - return 0; -} - -void CVideoDlg::OnShowWindow(BOOL bShow, UINT nStatus) -{ - CDialogEx::OnShowWindow(bShow, nStatus); - - if (bShow && GetSafeHwnd() != NULL) - RebindVideoWnd(); -} - - -void CVideoDlg::OnMove(int x, int y) -{ - CDialogEx::OnMove(x, y); - - CRect rcChatBox; - - rcChatBox.SetRect(x, y + m_rcVideoArea.Height() - 126, x + m_rcVideoArea.Width(), y + m_rcVideoArea.Height() + 24); - - if (::IsWindow(m_dlgChat.GetSafeHwnd()) && m_dlgChat.IsWindowVisible()){ - m_dlgChat.MoveWindow(&rcChatBox); - } -} diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/VideoDlg.h b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/VideoDlg.h deleted file mode 100644 index ccf65a27..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/VideoDlg.h +++ /dev/null @@ -1,180 +0,0 @@ -#pragma once -#include "AGButton.h" -#include "AGVideoWnd.h" -#include "DeviceDlg.h" -#include "AGScreenCaptureDlg.h" -#include "AGDesktopCaptureDlg.h" -#include "ChatDlg.h" - -// CVideoDlg Ի - -class CVideoDlg : public CDialogEx -{ - DECLARE_DYNAMIC(CVideoDlg) - -public: - CVideoDlg(CWnd* pParent = NULL); // ׼캯 - virtual ~CVideoDlg(); - -// Ի - enum { IDD = IDD_VIDEO_DIALOG }; - - enum { - SCREEN_VIDEO1 = 0, // - SCREEN_VIDEO4, // 4 - SCREEN_VIDEOMULTI, // 14С -// SCREEN_WHITEBOARD // װ - }; - -// enum { -// WHITEBOARD_HOST = 0, -// WHITEBOARD_GUEST -// }; - - HWND GetRemoteVideoWnd(int nIndex); - HWND GetLocalVideoWnd() { return m_wndLocal.GetSafeHwnd(); }; - - void RebindVideoWnd(); - - void ShowControlButton(BOOL bShow = TRUE); - -protected: - virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV ֧ - virtual BOOL OnInitDialog(); - virtual BOOL PreTranslateMessage(MSG* pMsg); - - afx_msg void OnMouseMove(UINT nFlags, CPoint point); - afx_msg void OnSize(UINT nType, int cx, int cy); - afx_msg void OnPaint(); - afx_msg void OnShowWindow(BOOL bShow, UINT nStatus); - afx_msg void OnMove(int x, int y); - - afx_msg LRESULT OnNcHitTest(CPoint point); - afx_msg LRESULT OnShowModeChanged(WPARAM wParam, LPARAM lParam); - afx_msg LRESULT OnShowBig(WPARAM wParam, LPARAM lParam); - afx_msg LRESULT OnWindowShareStart(WPARAM wParam, LPARAM lParam); - afx_msg LRESULT OnDesktopShareStart(WPARAM wParam, LPARAM lParam); - - afx_msg void OnBnClickedBtnmin(); - afx_msg void OnBnClickedBtnclose(); - afx_msg void OnBnClickedBtnrest(); - - afx_msg void OnBnClickedBtnmessage(); - afx_msg void OnBnClickedBtnmode(); - afx_msg void OnBnClickedBtnaudio(); - afx_msg void OnBnClickedBtnScreenCapture(); - afx_msg void OnBnCliekedBtnWhiteBoard(); - afx_msg void OnBnCliekedBtnCloseWhiteBoard(); - afx_msg void OnBnClickedBtnMore(); - - afx_msg void OnBnClickedBtntip(); - afx_msg void OnBnClickedBtnsetup(); - afx_msg void OnBnClickedBtnfilter(); - - afx_msg void OnBnClickedBtnfullscr(); - - afx_msg void OnBnClickedScreenshare(); - afx_msg void OnBnClickedWindowshare(); - - afx_msg void OnBnClickedHostMode(); - afx_msg void OnBnClickedGuestMode(); - // ڴĻصϢ - afx_msg LRESULT OnEIDJoinChannelSuccess(WPARAM wParam, LPARAM lParam); - afx_msg LRESULT OnEIDReJoinChannelSuccess(WPARAM wParam, LPARAM lParam); - - afx_msg LRESULT OnEIDFirstLocalFrame(WPARAM wParam, LPARAM lParam); - afx_msg LRESULT OnEIDFirstRemoteFrameDecoded(WPARAM wParam, LPARAM lParam); - afx_msg LRESULT OnEIDUserJoined(WPARAM wParam, LPARAM lParam); - afx_msg LRESULT OnEIDUserOffline(WPARAM wParam, LPARAM lParam); - afx_msg LRESULT OnEIDConnectionLost(WPARAM wParam, LPARAM lParam); - afx_msg LRESULT OnEIDVideoDeviceChanged(WPARAM wParam, LPARAM lParam); - afx_msg LRESULT OnRemoteVideoStat(WPARAM wParam, LPARAM lParam); - - afx_msg LRESULT OnStartRecordingService(WPARAM wParam, LPARAM lParam); - afx_msg LRESULT OnStopRecordingService(WPARAM wParam, LPARAM lParam); - afx_msg LRESULT OnApiCallExecuted(WPARAM wParam, LPARAM lParam); - - afx_msg LRESULT OnStreamMessage(WPARAM wParam, LPARAM lParam); - - DECLARE_MESSAGE_MAP() - -protected: - BOOL NeedShowSizeBox(CPoint point); - void EnableSize(BOOL bEnable); - void CreateScreenShareMenu(); - void CreateMoreMenu(); - - void DrawHead(CDC *pDC); - - void InitCtrls(); - - void ShowVideo1(); - void ShowVideo4(); - void ShowMulti(); - - void ShowButtonsNormal(); - - void AdjustButtonsNormal(int cx, int cy); - void AdjustSizeVideo1(int cx, int cy); - void AdjustSizeVideo4(int cx, int cy); - void AdjustSizeVideoMulti(int cx, int cy); - -private: - CBrush m_brHead; - - CAGButton m_btnMin; - CAGButton m_btnRst; - CAGButton m_btnClose; - - CAGButton m_btnMessage; - CAGButton m_btnMode; - CAGButton m_btnAudio; - CAGButton m_btnEndCall; - CAGButton m_btnScrCap; - CAGButton m_btnMore; - - CAGButton m_btnShow; - - BOOL m_bLastStat; - UINT m_nScreenMode; - UINT m_nBigShowedUID; - - CAGVideoWnd m_wndLocal; - CAGVideoWnd m_wndVideo[4]; - CAGVideoWnd *m_lpBigShowed; - - CDeviceDlg m_dlgDevice; - CChatDlg m_dlgChat; - - CAGScreenCaptureDlg m_dlgScreenCapture; - CAGDesktopCaptureDlg m_dlgDesktopCapture; - - CRect m_rcVideoArea; - CRect m_rcChildVideoArea; - - CBitmap m_bitMenuInfo; - CBitmap m_bitMenuDevice; - CBitmap m_bitMenuFilter; - -private: // data - - typedef struct _AGVIDEO_WNDINFO - { - UINT nUID; - int nIndex; - - UINT nWidth; - UINT nHeight; - int nBitrate; - int nFramerate; - int nCodec; - - } AGVIDEO_WNDINFO, *PAGVIDEO_WNDINFO, *LPAGVIDEO_WNDINFO; - - CList m_listWndInfo; - - BOOL m_bRecording; - BOOL m_bFullScreen; - BOOL m_bFilter; - BOOL m_bShowInfo; -}; diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BACKGROUND_VIDEO.bmp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BACKGROUND_VIDEO.bmp deleted file mode 100644 index b4b583b71fed9bf14a2f2ef7cf6c00c527506ca9..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 27704 zcmeI5+fL>-5XWh6d)KQzLZ6`ObyYwsfk40wLV`-LfMCm+3eX-nilqX?L7ZWqwLg){ ziX7XYV|$!@Xd|(5CiZydAJ2F^cE0^%@b?cruh(z<`zwEc{r~qv&o7jEdVb{j&p#D^ zuLS=2GyB!o*EcvgI5ILaK0ZD*H8nFcGdnvwKR>^)u<+saqQEUg9#Mg6RHg|HvkRN4 zLsT0c9-f$(c>n(W-w_whVFIhSfmMHh|Jc~r^z=02A_5gdQy9V)=5&$i9VhLESBz;S zhoy=XUC&C!|L&9Xv-wIK4 zdZc&n-Vxd6S2LzZ1V-#MKE=spU|^u-Hf4hmu@T;>Tc_CO83L6ELJ*|w)l8uRxzP!Br^z`(tWfvkLm{DLG(I=&bGY`lF zo}Hbw44!X@WW&KmNAZqx8Od8)a|iw7$B%8p2ay~C+a965!^%J}IKh5@f8QR65XOdp zn~wU9Ar!L+-QVAD4?cT)du|*YPaR9wn0+gp;lsm28z4fAx}LcV7a$l-EIuG?i5Cj< zJY|TC;Uc@Vy3Lt6|J!eG%nAn;S*x%jVI3Vpe7O0Yn|ail4d4oXh3UpFcl7J~~k1z2i|24-c7iwzs$cdA%rn`t%7R zkKE%Bo1%+yj|t0a78A{b5sDBxYSA@X9~~WSZf^Rh17=j#fPx`xW8$2SU8}rVz=E_R zbFISC($db(4q1?^t1I3(w_1gcw=|(4%}-8FVAZjHd<9^^1z~0JtYSFeI#B%J;Na`m zujl9I*c1q0To6}RS7SKGw*{QK*`D}L3l4?dU0zP6pya2uYoSP`}NcUa5!4* zSvgfTECtt5D@G#O#fTF1Hb(7=L)ykiLPVTxaDWY@c|4EOy*Rs zV{yB?yV7zh{w&0@?EofB5FH;MD-}cwfD@DR@t2K}Cz)7;LW0Wd`^C{4lo5cW!C74mW zcp{!tVzg9wk}ryv*2tmwblUhRo=Co{s*40A$)2E5-{QM+R?&eqmeRTl}0(EP6UcjWd5-J63+ zup&MbT7s$lL99$@m3n%5ngj#~6Lvu2{Y;eufE3QB*o9AfK0$Ry+R&j|l1HR%Rd)#s zq#g%5giDKhPRORDox8aUjF4k4kzgK=r+qZmSR3o%@T&tRxqhmjeu zk6(R*RSHlPZm0aO+$^@XwuT|pRo`8oeKfWjtEwfTsF|yb4`sQ%9%7-$ok0yQg3lyS zRG9#R28+6lIUio_NTU$NC4q>5N676I0z1x!$9!L)p<%pb6h#^u2}vBjk$DoL`}+b0 zlH5dJ$d4}ycGv8qc^)|n#!8#km1U^{Lr7@3T9%nHP%AEClZbt^G6#t=iaS0|Q4nQ2 zF$GF2Kpbl{tclzXj!Sx~{DZs?gy85@aM1S9}fCzWprJ*%q$N%7%kI^ydcU@eBz%f5H<^xN)4lz|1Mc0TL z69kqOuT^H*(sElvys))ZEgT$`S@vd5hNzjSV*$bHuF4&n#yldklp*Wb5fD`YVf>R_ zF^c=Q#lT742LF7JQZ2H80Ep3uxADOW!HB-(_R$>Z(J5WG78wmaydt}_8RBiaprdA; zu%^5JE$)%g&RLPbuGrTBCj e(;%|NbrfIfF)FwST8a-tctnL}|9`8Vp8o*qkI`ZP diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNAUDIO_VIDEO.bmp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNAUDIO_VIDEO.bmp deleted file mode 100644 index bcf55f4bc8d610ddb215a17c9938c8358a703a8a..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 27702 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 M>?HJ;v}`8n{}R@r^Z)<= diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNMAX.bmp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNMAX.bmp deleted file mode 100644 index 67d9c69f6aad84accd6963832edb0307bed751e1..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 5862 zcmeH|!3}^Q3`Oe_#u1#r0la&600(poCvgp|zyW9=jWu5U1W*e6w2vzDa`xoQ#Qn%^ z<#wAo8n`FgsRU(A_w7H)vjL&4uKUofJ6G#ARqpm5Anw;9%+VD-tD)ZT|xMr m8!Db>H&?!+94Qp+QP>qqw~MhNii`=?g8&GC00@A9CvX8_8>;vK diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNMIN.bmp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNMIN.bmp deleted file mode 100644 index 75ec49c88fce5dbe8ce54e9f56f98fc3f471a945..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 5862 zcmeI!!3}^Q429vkgmDBXZ~*V#9l!w{!%1ADJ_+Zh3B-#(fhIs`;Om8TyGJW+QJgh) zjdy9VNzv@A`(;vto6`|M009ILKmY**5a=o3VN3i!kIRFexoU7+TbT^u8$Qa={)+Yt Z9UKxBPgR6G2q1s}0tg_000KV{cmPX9L)ZWS diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNMORE_VIDEO.bmp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNMORE_VIDEO.bmp deleted file mode 100644 index 3d66409df0d263e7c1cd5e61a2f05917eba0f8b9..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 27704 zcmeI5yGvz99LG)CbgA+e#20SVXjF7r2rDYA;0r+$5N)(bVWHS8TWl9t*hWEYEUW~T z)ih!i^A8BNHg;lTC1McVe7FO{I5TJNoX0(9Aameeelx$PXTEpNJbq{Vb-e$NrrPxj z-z|Lp=F`dNo2DQ5Zfg1#{`cRBPpyKlAJbpm-QBaZv+L{YpFVxs-QC^a-~Up(AShA^ z3jxH^+s>lV(b2K8vV!aL^YiQL>$|(Ve`^;6MJiz-fLIpm>2*Sjr@g(szrTNYczAq# zd}d~5Zf@?k+66(8N>~UWmi})|q0!aVwY0RfwYBw^_k}Pjot>R2+<1%j^z>|OY@D5) zJv=;o^|%m27!?$~oum*9EuOZvw%4y;Pfkw$?tLMQ3W_QIY!6ZH3|-36(UCWBUI?Oy zdV#I>>eZ{ypFiK<-wV_{KRlqW!^0PV$W*`xrZDK$Bnd(-EiLcgzrVe`^#P1q1|yilV1g^J>d@k8Zf<__ z=1pegs4&6^rZDJrBWyy0gM-`K+nKMc;vfeDvlzEEh^vl~ULoC%2{6oJ+~wQG3oV|$zCOmo z`2k~Ez%0gX_aL!uVPWCqZoEI7m4l-#@gE29^JjFD}F#yl!)R2p}V;WU76(3nSsjY{Lr@hb~09!9ne8uKKf z2zN=tX=c`i&$d*kB+)pvPU@K&7e3okp^`-7)HLxYq6ui^GL15@tghuC>)^I?0lsTq-7Ut@YBO z#lzxoA&Z3BP={-6b(;N!Y)xO376GV`W`99#(DG>l2ss}17qT^dQCb8b?+^Q%nfJDe z!Vdw+ZC3gsxwln5a)d_$kX>SE@vy&HVdo7uAjAu|pW*{-jFD$b%5KE@6mx$g)t|u_~G{!i*#Bkmw0E9s>p~b_%)!nRRatVe+!7>rz_C+ux3RZ;~(=Wk<77vMnWg^7w zi(o3Bd8vpZ7;;U`cC4y~U_y(BTvK-X_N3-VY>gx3L^ycQq zWIa7S{ZqRjOfD)YqHeOx8iENe9yV~@Z7R5IOplF?F&;35$(?^!yC6(1Dk!3EvdkKS z;iU<)9krSdA3pq4yI2X?+}u>TUQ7tAa!E($J$1|ft|5nPO@idLFnLW{>|!*q0Xlr2Rr#pIqkt{-ZcQHylWTxw0VG{FS5en>EJ|H1)@xPKwL8Y{v6 zMchBN;wSE(S^=X~vRK3xe9YglLMY~MXlT)jB7Xz?#QZTUeq#QZ1{kd<^T%TTs)?VN zzp9}{E2{acbU~HR!U%vc#REi-{pw+6HBW5<%B zVmMv+j0}UAP4eij=OGX)AdHGU z*vD!%e2dK!v#T+N_ravvUNC3P5%L}mWCGq diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNMSG_VIDEO.bmp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNMSG_VIDEO.bmp deleted file mode 100644 index 7da4eb107c5cc0d06f31117bca56a6c716b20d5a..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 27704 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 fh>;M*P62^T1eV7Y>0 diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNNORSCR_VIDEO.bmp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNNORSCR_VIDEO.bmp deleted file mode 100644 index 6e043f8732b310fdb3f4e563cac9aa4966a41ba9..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 6966 zcmbuD%S&WO6o=br0%0KQymf|&1mBO)cKeLu6V2G5_(G9^1cEO7141_02W)4|K!}rw zZ!q9%k%izYAXz0OnGA!A5RGqK34)4aJ}f+Qa@*^zd;8Me{JQGYx%YmYI#qS<-4DML zy1c^te#rL$-#7WDT>c{H|M?B`<=^F%nVDHsR5Ua+R9;?=PUeb6qibtxjg5`TIALt0 z@Xk+PyzJ6_QEcDk%>b*#CM8IilYwPXp?d`!yR{Q(=SA;IMwzjIPtBpZZ zQxidTczCGo-89qc*+{A&`u$;ARrt0sZYWJBsGdJgbsMYOnO0!ABGlW_(IJRTS9f=} zw!cAx2o8d1e0&^4m6esVv$Ll0hOxS3ri zqTk|a6(8MhEK7%s;g*^C!41Qui)p11wYRquGemM%SC`=?mY#yl!{ib~V`F0iheprg zVnF86h&DDh1P+MA%u|qgm|PM?zs6q`I5c_=7lTAZ0tZB5W+TWCOfEsBh0SoWsjaQu z+1ZgO(n4%(M0H8VpO0Q55>~$Wa3c^gxn!bgVe=T;hU9!LB5h-%NzU8b+nS8gHelWb57v+;YK>=1dbnasm?ip`MALW zlnoQHaf9P`e!0Q%m48_B^eV66pyio81%6n{bzL76%sd7A9KD3; z;PJ(W1)Y740}FqbmX?Nxhdm!d3`p{_V7*Y+`T6Z+J|3O0dy!4f#TKZNGLyyZDu z3|P?F=QyyKzp+?M%#sxGcsvmuE%Wp9zD`>!D=WfG$JNo%5oZDWhy3x2TS82WzrRh1 zRlR5LNAIyU!=9d=;^Ja^Ki9&cabaPBly2`wGtv6w|>FH^If4?t3nu+MGC!tS2dE1vC%|tYC$*P9o&{1q%(aHOsASuYYSTCgARi%9q^E-val zB#3-f9RKaEu=ZBFbxZ(R7{Ata%|H;bfuYFnW@gh4A|fXl bIOZ-OB65;}WBh=K$Vmo{@dF|v$H4gyhX>9A diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNRESTORE.bmp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNRESTORE.bmp deleted file mode 100644 index cd1ef0e24f086fbb908ad723e78ad2d1aa74ef24..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 5862 zcmeH|-3`Jp41~iHh!L280eI(~0T_@mn1nTg^P?hk=gQ?C>nM%j5`Xa>Qn}vV$I{2e z*0Vi#dzy48CtFK-&i(#nF16I0nLs9x31kA9z&{C8XN3P*9 z7dkaOJ4{X{kO^c0nZVu> F_yEt$dB6Yw diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNSCRCAP_VIDEO.bmp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNSCRCAP_VIDEO.bmp deleted file mode 100644 index e217776fa475eedfed3e57f10f5a4ddadcacd810..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 27702 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 Q_MA*Yl?*0%;7*$V0Q=TlSpWb4 diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNSETUP_VIDEO.bmp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNSETUP_VIDEO.bmp deleted file mode 100644 index 557d3a5159bdbf6600b9c0aeb9476b856abf94f1..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 6966 zcmeI0ze)o^5QignYODntZNx&-2v_6~#FXJk$_N%dMJiKYkuHU`jo}IlgXxpPm+%oR zd$#Jgj@IMm+{?Mr0rEM|G0 zmu2~442Li_L$7x_o%wwJWekT<9~aABXD8F)!N=n+4-R2$hF)*ATHS8<)))?SOXC>27|$!Fv1#$*f6jekH?uY972)` zf?$db1DoY?d1VZTkfnl?l;U*Qgv@NTmtUUp;1E6!o668&iVXvsq9`tm;SiGiJ!vwT zh~1&Pu(1)@y( zSY)I4EEbEk@Ogb$51(GIX94=Y>3sRf*nGO5!+fZw{%#Q^4uP$b&QSmkrF0Mb_{jbq z)j6v8A?fI!sLoNv4@sxLM|F-Wen>j~J*sn5@k5gSzEOM-nNt7M=HuwY+I-N5c3-9Q zw$Nzu+jgO-bB?q6c@^SQ`85V diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNTIP_VIDEO.bmp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNTIP_VIDEO.bmp deleted file mode 100644 index fd7da2ef347d37157e99b821cb68c4d8f29bb284..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 6966 zcmeI1ziU)M5XY0kMlgk-h*nyNMY=!&nh>}y$Q7wVJPYxfGyw|>5iF7v76}&V6hXl> zffVNa2U1x2H$*$NPRiu;!yB`=Z{N=Bgx83;ygO%SXU5y_n_s)>bf<5ORb!g(JA5AT zxyEO_`i5Zr^MrhuRpWMU%*@QJtgLKpZSCyre5?ipQb?$Gtao^Vx%|`!6njd3E92n{gfprZ8E`Y2#1O9kgwYH)J32a2fT^(&LwKZFryk$G z{`K{^hD^*y4B@)=XvW)IUS2k_`Ll?a_UilnzTq}CbgBu$sEmHZ8MU#oae8`ML&2ON zjLMnz=-=nPD?fC%iNO&XVN^!?XB2_#K_-@I#y-xVfkUofH1UChO5#O0Ll&IjaJXL$ zh$dR7BwmCwXyAN!dWolr4;)kyFTxq(jmI?6#E3aD9eWY97FHl5??HnI#bAnLqJ4r#gL20w^{dqxw^V4b|5qv)J2AT zo83Fi?d@%mfzV`77a8(x);(ap>|Yic2u%ick!pL9AMk%5TaCZ+{L-o6%DPJB?u z2r+9^D-S-XV}yEbR4WfYsAGh;A8$6HJ@}x45dvRx3@1K_VT1tG9K-29h+%}5Msp0O z{~(4DTABotcK7@V1&~{dwej$>7hM77~$;D9v_TwdWZo@XeT}xvGFO^cfq!ZPqDrW zwnco3^(i}^VqU=zjs91yUHVt!6=(5B>PyS{I3ZcbMNBB0SEiuIk1)7voYGKZtu z^_`8=+wj?9cCLfZMX7+=owX)(T>=hI?*InSrX z_=?Y`pk&-{Xki84f4`x{l!4d*Z_lx%h{ZHP{hdr`=UMpQ6 zjWK5j1_V=>MPz~z2ppA`hU83RT>W|H7=kHG&4*+4KvTA8X-LjA#+)5^Aeh1o6)gxG Y1Z9hshU83RT>W{c2f-9(sA!4$Zx9ZWng9R* diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNVIDEO_VIDEO.bmp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_BTNVIDEO_VIDEO.bmp deleted file mode 100644 index 78e342585fe75e154d165b46485ef47580472109..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 27702 zcmeI5O-xls6vrQl#>7Qa7fqX{3pcHRf`E#Ed=$}CF<=n2N}G__q}s%V3yEp#!ktN@ zr5jSyg@~pW6s)326W!E=eG^vgs-~uC9#&Sy=tldyZ(x`=_ujel?wj{8c5e7MGjqPU z^XJUhx%X}FX*{0EU5)&#-et7yu(i}+GpMn-=ZRu`JnKtp`qd6!Gl9XL+8$& z8yy{;n3%YkyC5i1NfQjP6|OstL`_Z2v17+DegFRb2M-?1&(A;4T@VzhqzMMt(r7PS zrn0i~qs~oVe%>;Argi3r_TR@l{+SNGAShBv6AZ8wt~-sy`t|FZnwoa*+}YF9vw#2o z!-o%llDi-%Qb`jGu%*#%EmL1#f8@xKk&%(x))&l()Ya8l8!3Qs^XAQ`PMx}Y_wLiD zPhVPGu)&N7f(4kdX05KS>hIq2{nxF3{oFDC%ZG_yu)&N7g4RX~V63jLZfk4n>+Ac} z`hpn|1Pd@@!O9IMq};f1!x}hwj0hs`u-9s9Ylnx2pFDXYQ1jx&3k&$XlxzqhjuMMM z-HL@s^2I>&pOZ_lc|6_l==$2Z@wex$uE}0mogG^dd|g>hkxH6ikN`svafjiENU~$c zj)8#zYvANDB8a$?a8y-Qb@b@bsi~XH~HZu05Vr?c6t4PeYXC_z>6 zz4mc$}g=y>7t;~mu2TWK4YEiD3 zN+t&f2dAf}i@->ND9SOB?8hR<$&)9aJ$n}JdRH|l$Hbzw&gy>l@X8k+$e)dvD zQGkgU&MHtV^jkux4B!z^w1E&KOGzV-3Ox)Z4rGihC5=2PqA-*=kTJ4|$n)shd#;hQ zH04G)5W-O6K*q@8HqMx}nFlgvwk4YLsIXCK%o(QB0KPBq`$BBasNGsl8q?bSVRP8YCSf|HVOrarCPv~sGIG{qB^98j- z%TMEg>JR4&LGYPwua#6Z_`v~r%t|bhXIte* zj1f)44UoP0F zc5y@a!x4E9e1d7SGC3(DEhf^qA^hQp+*KGUMh|WXe+o*;CJVyL5NuvH}HonFLSq+vlVB^@*+`3=2|QlcyItW zaE6Ji$mg*=RWAj`F0TSVxPdcFT+Q8D&Q_cuQP2h<=g*%fUTsXe;DJ+BI6gj3vRh|o z=h)boS|3T{42gm^n3B$(#-kx zSDEcKncB4pU+}=G#+E-uGRM0!yXrH)eVbRW@<5AOG|rGHXoHa6-d_5OjWzQH51gvP zLx&Evw6ri6J#gTFS|3T{jOEI!y}dmNI}7b_N^G1xd$zf`Su}9EB@2jyDP`~7yVup#B^oYXyeRAA2%I6;G#I?DuhlwKD|Xc;AV)$APAPkBDAQKG zAo$&9OZAdL5;%YxI76;!WLIjH+;cN>WGkFfcF&$Ygj~^Nv&4gkbmh3-RO=VOVfPC` z5q4De6DLln3L|NpAzeAHH`RJe@CY^pMc7fL*!NZyM$$p<^qFAtL(-t^%1A=O!-hbE z2sgJpqOsZF z2WQB5kL*gVQbj@{jVx%<*lh5FGi1C6_#q9|II&TYkVvBnv}kMz__?|UH*kg%-o$Q& zK}A9$4L@kn*lh5FGdwh*K_#-Nfx%o%jUSvLP-swzENWmd7gOU0XLx9Wjtg>_mlZ!a zfEzetd0?u6!CXv@ADrRIn@GTDm1e+bt*P;YGdy_{2^g)?3>d97HGXi0=WYW0ko~^A z_!(P)8#u#a$gQogcu0_{IVH5anCQ)cmDkej9mWx2?qQa-k%`;_x<}@ z)EF41{rg+O_e87l?~l@Mh*tFPkJ4^PxCn$w`W7kw{yMol&m&%o_tyzHF_4w$T~hx2 znR%F5OpAS;-k&KT#B|#EiVTH@7mkG^p<2Vt*7=GIg@y^UYCTN*_xFbHiB`kPntdTB zTZ6se>M2G}&g5*2x5n?ylOldeq0I}c6dKECNW1jQhS*?)eM@$;K_j6L<|H~j|$ CFVj*0 diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_CMBBTN.bmp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_CMBBTN.bmp deleted file mode 100644 index f47646e74810fec5dc230a3d28079d05ac5318da..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 1350 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 zuY11l_3y*_*ZaPAeDd?js}32nc2tj98eTv2ePiDG^HxRp zEANW{0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C7 z2oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N z0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+ z009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBly zK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF z5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk z1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs z0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZ zfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&U zAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C7 z2oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N z0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+ z009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBly zK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF z5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk z1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs z0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZ zfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&U zAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C7 z2oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N z0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+ z009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBly zK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF z5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk z1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs z0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZ zfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&U zAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C7 z2oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N z0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+ z009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBly zK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF z5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk z1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs z0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZ zfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&U 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 z009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBly zK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF z5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk z1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs z0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZ zfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&U zAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C7 z2oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N z0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+ z009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBly zK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF z5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk z1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs z0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZ zfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&U zAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C7 z2oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N z0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+ z009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBly zK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF z5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk z1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs z0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNYQ zuzma(-vkH{AV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF z5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk z1PBlyK!5-N0t5&UAV7cs0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7cs t0RjXF5FkK+009C72oNAZfB*pk1PBlyK!5-N0t5&UAV7dXjRnSx`G4=FqEY|= diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_DLG_MAIN.bmp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_DLG_MAIN.bmp deleted file mode 100644 index 3f873f1e55d6edd5442da200d7d73437afa07650..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 1080056 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 diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_MENU_DEVICE.bmp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_MENU_DEVICE.bmp deleted file mode 100644 index 003c466f004b1d1f744faffd9205d3dbe8cd2da9..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 822 zcmZ?rHDhJ~12Z700mK4O%*Y@C7H5FULpTufKQ+Mn_wQ%UoH=2_gnReyVKwgo61aBl zT5)l4OH0d?DN|BXQjQ-#4w3x$@gqdRYH0H;r%hUg_yJ+j+K zau3{vaR0(ZCQqJRQBkpN+qSP?zrqE945Z+MGGDxSF>&HVpyCZ1HpIur@7lEst{xZ> zNYMpl0)6f4>wEO*QJ}K6wzjaaFy#0`N)AvaFy-|2_5uTW&YU?w^S5r@3QrGki!d3$ Oqyp3h4@pb~1VsS#3v}lI diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_MENU_FILTER.bmp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_MENU_FILTER.bmp deleted file mode 100644 index 34b3d1d7d511864da498a38c170ee37e95821a5c..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 822 zcmcJLJ!*td7)1@)K*}s3E0_g@bP})s*LAzDlOIu*<+~C__F%w&`KD>!lrY!u%d&haVXom} zPD&ESulKQSJ5AHWR-a1S?f?etdESeX<2WDxh-qbj`@Rpukf`f=Q55q$%WDuRnE=3m zS%+cZ|IwJHnPr*eiIhwLV3%ne$0SJ%!{8;C5<{e90+2m^nx?w0+qRWGk&;Q4H}${L CL}-Bk diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_MENU_INFO.bmp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_MENU_INFO.bmp deleted file mode 100644 index fe7cbf386e954bfcbf03dd9cab05cfdf414f4661..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 822 zcmb7?yA6Xt42FraK+24e2^b)K(os>t2oZY#6;QAObOb1%fw_`TX9UP6*C!Z5rWLBRyvQ8u+KOV9IyAV7H z*?2~aqR99Cwrv%TNhmG|tBY`uVHj3KDYzg=7Rn=I*L8}cOj1LW1}Rc`^E}V8Oo7m3 z8g@HLlEiVW_|Rl@bfjEqn%exPX=KheUxkY)d{Wr;)OB4|m5P#jXu#yALO@BDfOLq`h6T_#Qc)(t!D`NGguZ7?H(Q;URhcB zs(?Wk5*LCV!JMC;6L~6?IyyS)A-kiCwL+oL(9lq!P_Pey#D%~N>AQi0gM(l&7>!03 z78XWFN6Y21I4>?Pm~DT5f2R|>ySqOXFgiUuh#A7qXT@T%Xb(mhTnLa|UthyyGMU!~ zd_G@)e}Ajh!o_}~6z9gq28`G1CE95N0};(u7a#>U28Dp2b0ZvigRAhy@@ z>FMcP1q?H!9`&qc^YimlQ&a3@yWJMD*=%w(vE0DGK&e#HN^L;mLVyf$*Yo~OK@Y(o z-M5{0Io&5GCv$Ui1hciZ<@fvZ`Me%}c6P?;W<`(3v$?scc?`OcxDX%{*WK?!(R0zs zjc2yx-RX474#Z+HR+0NqhHzVQLAhKmHbEF^=|bX?>r}|Ud@tm6;N?mtlUxGJ%ggLf zHk+0ALa%;xbww^XlA6Jw3yI4lu?dM?A|n(Db$j3URL{m!LR50nHThtJP$_SA{y+Y| F@f)p*!sY+~ diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_NETWORK_QUALITY.bmp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_NETWORK_QUALITY.bmp deleted file mode 100644 index 1e2c83956da67d8f827ebce55b132900aab6933e..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 21558 zcmeH|L9P@r3`B=JuwcoO6L0|b>^K0Y<6PY2V__(@{3c0t5;=CF5^jzUEi7UCLfQfAtEVG%7xySx0H{ovhUAZ7 z+^b#6UOs2I!Y7T2&u7+AT6`z#c#`ip=RD#^5rk}2uPX`MwTs^UuoTYwbvy;D*2&Vti3wN=W~q=yrC`<0(R@CgbBZ3g6mvAD z3RW$hp~Puk)8;4wmV)!2Qwmn?9F4zPz*0DT(x?=yTJo876ah=&WF1ezs&%rCN5IG9 zCBAA|1TDn8=BcBQ(^B|G9Hm90?$9_fa#{-cq)}9j#hraX=!^RVFib(A4i28YIpDLyR7CymMwD+9BRqWG|IX!K|&RkUuztfPpQe6=i| z(!v(H%voO*9SsY|qbNQs92z}=)n-P~xeK$7BH(a8 z+>3Dm=oucIt(-6Cj_ z%4^1{6#lK2`$Odxu$W03&ZiLiEooHxg#IaMRQiPeDQQK~awey=eR!M}+EaxPe?_12 z^De|rDBK?^6Iew^<1dnVq9BdR1XdB!sK`7~kX96~3YE@%3oV>f2&B@vML7z7-lgcf zT5i-Xa&kDI!@o}8_2+jF>qdpBjeg5l0UhAiXzIgU? zIG?khoe@3V&+zA3E-q(qTKvu<-8wq|zxT)Wr|18#^ZU~~r)L6Z0%rne0%rne0%rne J0{{60egNq%6*B+; diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_SLD_HOVER.bmp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_SLD_HOVER.bmp deleted file mode 100644 index c6d601a58896667bb4c5d9bd35157fd7b0393be0..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 1782 zcmdUv+int36oxUyLJ#%;+N!i#w5CW>Lu`UK^+vCK6BD0DX=;GsG@NT6puT{YzC_bo z6K3}8?YH)f6`@$YF_8?DeOUY7|62dQ=GB{T^D+A?^3L(U8~tzCQ7m>A?c1Q}Wn$*P zc-~e&7v6tOmCh3%M~UMR1EwtgIr(?xvsCFKUN(t}Nmfm=q8F-~!F)yEtQfWkxEAg8 zhc6aEFIM#}N3S@+YAsl+>6MyZc7jDmCn|cbtO@%KR0zWDAaFL_(03ZahJ6^M>nsLr zEmRG}WO$2=XCZ7ZgrZ8imJnFOn5y>u~=9YVw_hMKI^HJ4_ZYR6T(Z9mub^F5XC`gFd&-(t;u0XLx0AVoa2nWY0 zrH{_3%xX>Fu1iK)SHXm{2SdL&9KAU44h9~WERrb!lpQHC1HKx^!D*-f4xFhfHGvFF zKsY=d9exrhSV4(e5nxjjU*Xaz9Qa7?+pU0Lj&QIz^j@BN;4p}A+KK@9aA^{p<6m%~ z$0Az<0I34Us#b~SZ5a5 zB7iz0%5OAVaXV8A%hs%P!s8Qf Tguo0xzpF=o{au{^{KwPpok=C| diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_SLD_NORMAL.bmp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/IDB_SLD_NORMAL.bmp deleted file mode 100644 index 23ec5c941375833576e3fb7493ecbe6d85e2380e..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 1782 zcmdUv%T7~K7=?caIE1N>VB*}ViF2RB_)fNILTQVI-msJwF;Eo-CMLW<8ERrLr>6&| z_^p2*>any{Cnl2Joz1?iv)1}A&tKd;H2-_b{FvXP^!LD5W~b@7UrMK2yZtZ5MdjsX z{>dP}^{ue+wXng0f7$$V^5?s+u5z2hqK!&6D%-HES&JQGlOrzt7VS&n8JCA3RBZG{ zV_dcIp61c6HaQw@8`suA1rRL}1_Fwk&#U z)3#>Dq@_)cQmAcPDo~#6h`eYt9id~>Bb#r zYzj!v;uD*_x0vzH;+{nT3RVcjtD-GLkeCKCo*{RL?mVB_}%+Y{4)CD-B zjwd|KQo71-5ePX`cST1cFgvsBPnMk9^@SxLg$X^B%Bx1|5_y%yA=4D5sxHXeuE->P zA>4e{5LEw;lH*8P*~rqBIBi*hCp?5qz+r(p@#$LB_P|vYTnJ=wpojlI`Jn4Wo*)M% zsV*#<>#FNAd@v-7bD49WNxyxIT4}I?&(OeXyb?%HM_eErWQcsu{o?at+_9+R>TsK= zg}5I($lRP|afe&TLn=af=x!5YWndU2Buox0YI@LD(#Zb%CpCX^=LV zy7<1LE`XZXDcVDwl1{wU^Se5QFyC5Jr@?lh_>ejeH4>Tz$>~GoNi!)K7uNTU0ENH- nHB0T&xV)7~EN#d87)MLXJiNU>6Txg>B~SjguinS}mpeZI>6QmA diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/ID_TEST_AUDIO.wav b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/ID_TEST_AUDIO.wav deleted file mode 100644 index 196920cdb46e8317ae1f657240b307c15e32b2ba..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 244886 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 B?UVoj diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/OpenVideoCall.ico b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/OpenVideoCall.ico deleted file mode 100644 index 0ac6e0fdbc5720eea3fd289ab462c3d060f5aea3..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 33324 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 VC<_1o2j{O diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/OpenVideoCall.rc2 b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/res/OpenVideoCall.rc2 deleted file mode 100644 index 973023e83d21f0e0b0bbbe4198b807c9fb3de8a1..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 812 zcmdUtL2JT55QX1a@INegEE@11Nb5nQDy@1g8WRoJ1fo6o=i7d7jV+WOJSxL(W_D)Y zyqU?@XQD)HwYU=n4YXCIS}QG8Xrm145o?e1^n%_es>`YI9q@jjrBM%hCMU(Nq9@mp zIO80MGDaZ(0SO>iO-_mCxQw?VYW^BM#oFui!_F*yI{5R*EhlfFnO-&5LQfiLsyFTl zRi_$j$lEz11JS%{GLG6sP63pH3K?(a81$FRO6$hIhR5~&U22xGC$sc)uVH%W(ebw_ jW@u)f{00enXSZduVejjAm)`0Bf69)jd&j*f_tEt?fU0XO diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/resource.h b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/resource.h deleted file mode 100644 index adddab1ed756850c6dd0d77b1b5284d87b93d1bf..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 12336 zcmbuF+io015QbYw+#n(G23X<-DH4fenqy$ zx*bV#kw$4-w3Bq)oX_5CxW56QEeo*c$qYjhElv5#Zf#gQa^EcvE7COz`fAIQAn$~@Nhj@6sn z;$m|b`c2f%iN2$+Hz99UkWZyi^m3GTEBUqLT`>>z8%g3i$suorGH;88X7R>i6Qw^r ztw8>^f;^ILu`oQppPGB{K?Qj(d5@~8nf$PVd?0CwQneDB)jg^p7i+6!uZM91d$t}t zk!1|iHDo_-7(wuY;m_WcKsm zMKYhpis$J`6ZsD%|A``MpROUtK4=l?Ogi2dbJEmHBa!>Q0CMbuMjopUnB7FC?JBK6 zj(u>rw511qA0$5!mx*&^Z(>JZjLUt9%&`xeHXzP*)cOfN7?IKFjx@a2l0D1RcZOW! z-DKE)OKZ0llaYDZHrj7T*W@bSp0Qc1jS3pQc(rm@3y}RDZ0k9<&_(Hb2HDp$GM8vP zOltD0?}NxZmp*pn*N+t~sH87+HPd~Uob6|jeIM*5Gh(FXWvtR>EnY+ReGsx`E3=Tr zcjG&10)L!R$Y?u~@OCSZ{rJ2XDTnspR$$M_YDB7;_hj<}%xo^)@1!t1^R8eC+ zh-+Q`0@=6ci>BVP5k#@OF3#;|F}c`=S=+GD#DgkNVXmjH=d$$3?Dt@i*~p9~PMXZv zZyk(({2naiRcii+K@UP^KIT{!LhgH_`|l++8IWrFhrnKt*^fw8ixTxu#I#sqz{|(AIA1$NRit{ z7Pb07Po@(;iomwn4zl8T)01e2r+ur2#`Zm@$UT-$m>t{~pOuALwx4B8Zp-Dvq&A(@ z%}JYI_C=<)J))CnR=ViqNLnBU*3*q$V<*MuYw5=Jb3&1Ol@%>?;%9|6d-$3b>^d79 zzN!T~wn3|*7%8&LBd^}~ul1qt4gI1xnAwZI(_cdvJC3pD^Q-mchO`pNo!P7O0cm5RQD|+PHFg|hnZaVbYx6dXBguCBSiUxP z?3c^YwU%z|*e@3?yOwM*Hd-0L=NXf;Vl+{IQU@-Nu$Og_?@jL5FVDmswlZgQ*qc4} zZ8Pm=Da=-|)2qf-j2-tSzC%@I6-2+Uw{^1F69+SU6~El}Hob!F^0#uC4`8?U$hV|C=Llh`j|pI1q` zD80!Y$5_~8n|>{HvE$kYHdeA4JC3oiv5!^Q(OMW5$G*4r+<-T0u&9wWRS#5}4}vP9 zi+%$0pxvmx7mg6Te(Ny(|ot>s`B|+GrpZ)NDDjC zdwa}49@>@cUGlb{Wx8+agXiWCn~q zNz5ma+tBx^uBbqFZmMkFcpJQ96%^JxRrNq5nd@KnEzER3@2u6?>rLCX5_2vYtR9=| z9d<~OTd@PyWU#H=6Zy={R(EvhB2%Fr=pYj^pXPIOZ+I(H9-W // MFC core and standard components -#include // MFC extensions - - -#include // MFC Automation classes - - - -#ifndef _AFX_NO_OLE_SUPPORT -#include // MFC support for Internet Explorer 4 Common Controls -#endif -#ifndef _AFX_NO_AFXCMN_SUPPORT -#include // MFC support for Windows Common Controls -#endif // _AFX_NO_AFXCMN_SUPPORT - -#include // MFC support for ribbons and control bars - -#include "LanguageSet.h" -#include "AGMessage.h" - -#include -#include -#include "AgoraObject.h" -#include "AGEventDef.h" -#include -#include - -#pragma comment(lib, "agora_rtc_sdk.lib") - - -#ifdef _UNICODE -#if defined _M_IX86 -#pragma comment(linker,"/manifestdependency:\"type='win32' name='Microsoft.Windows.Common-Controls' version='6.0.0.0' processorArchitecture='x86' publicKeyToken='6595b64144ccf1df' language='*'\"") -#elif defined _M_X64 -#pragma comment(linker,"/manifestdependency:\"type='win32' name='Microsoft.Windows.Common-Controls' version='6.0.0.0' processorArchitecture='amd64' publicKeyToken='6595b64144ccf1df' language='*'\"") -#else -#pragma comment(linker,"/manifestdependency:\"type='win32' name='Microsoft.Windows.Common-Controls' version='6.0.0.0' processorArchitecture='*' publicKeyToken='6595b64144ccf1df' language='*'\"") -#endif -#endif - - diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/targetver.h b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/targetver.h deleted file mode 100644 index 87c0086d..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/targetver.h +++ /dev/null @@ -1,8 +0,0 @@ -#pragma once - -// Including SDKDDKVer.h defines the highest available Windows platform. - -// If you wish to build your application for a previous Windows platform, include WinSDKVer.h and -// set the _WIN32_WINNT macro to the platform you wish to support before including SDKDDKVer.h. - -#include diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/video_preprocessing_plugin.cpp b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/video_preprocessing_plugin.cpp deleted file mode 100644 index 94abcb42..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/video_preprocessing_plugin.cpp +++ /dev/null @@ -1,94 +0,0 @@ -#include "stdafx.h" -#include -#include -#include - -static void LogMessage(char *msg) -{ - OutputDebugStringA(msg); -} - -class AgoraAudioFrameObserver : public agora::media::IAudioFrameObserver -{ -public: - virtual bool onRecordAudioFrame(AudioFrame& audioFrame) override - { - char msg[256]; - sprintf_s(msg, 256, "%s: samples=%d, channel=%d, fs=%d\n", __FUNCTION__, audioFrame.samples, audioFrame.channels, audioFrame.samplesPerSec); - LogMessage(msg); - return true; - } - virtual bool onPlaybackAudioFrame(AudioFrame& audioFrame) override - { - char msg[256]; - sprintf_s(msg, "%s: samples=%d, channel=%d, fs=%d\n", __FUNCTION__, audioFrame.samples, audioFrame.channels, audioFrame.samplesPerSec); - LogMessage(msg); - return true; - } - virtual bool onMixedAudioFrame(AudioFrame& audioFrame) - { - char msg[256]; - sprintf_s(msg, "%s: samples=%d, channel=%d, fs=%d\n", __FUNCTION__, audioFrame.samples, audioFrame.channels, audioFrame.samplesPerSec); - LogMessage(msg); - return true; - } - virtual bool onPlaybackAudioFrameBeforeMixing(unsigned int uid, AudioFrame& audioFrame) override - { - char msg[256]; - sprintf_s(msg, "%s: uid=%u, samples=%d, channel=%d, fs=%d\n", __FUNCTION__, uid, audioFrame.samples, audioFrame.channels, audioFrame.samplesPerSec); - LogMessage(msg); - return true; - } -}; - -class AgoraVideoFrameObserver : public agora::media::IVideoFrameObserver -{ -public: - virtual bool onCaptureVideoFrame(VideoFrame& videoFrame) override - { - char msg[256]; - sprintf_s(msg, 256, "%s: width=%d, height=%d\n", __FUNCTION__, videoFrame.width, videoFrame.height); - LogMessage(msg); - - int width = videoFrame.width; - int height = videoFrame.height; - - memset(videoFrame.uBuffer, 128, videoFrame.uStride*height / 2); - memset(videoFrame.vBuffer, 128, videoFrame.vStride*height / 2); - return true; - } - virtual bool onRenderVideoFrame(unsigned int uid, VideoFrame& videoFrame) override - { - char msg[256]; - sprintf_s(msg, 256, "%s: uid=%u, width=%d, height=%d\n", __FUNCTION__, uid, videoFrame.width, videoFrame.height); - LogMessage(msg); - return true; - } -}; - -static AgoraAudioFrameObserver s_audioFrameObserver; -static AgoraVideoFrameObserver s_videoFrameObserver; - -int load_preprocessing_plugin(agora::rtc::IRtcEngine* engine) -{ - agora::util::AutoPtr mediaEngine; - mediaEngine.queryInterface(engine, agora::AGORA_IID_MEDIA_ENGINE); - if (mediaEngine) - { - mediaEngine->registerAudioFrameObserver(&s_audioFrameObserver); - mediaEngine->registerVideoFrameObserver(&s_videoFrameObserver); - } - return 0; -} - -int unload_preprocessing_plugin(agora::rtc::IRtcEngine* engine) -{ - agora::util::AutoPtr mediaEngine; - mediaEngine.queryInterface(engine, agora::AGORA_IID_MEDIA_ENGINE); - if (mediaEngine) - { - mediaEngine->registerAudioFrameObserver(NULL); - mediaEngine->registerVideoFrameObserver(NULL); - } - return 0; -} diff --git a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/video_preprocessing_plugin.h b/Group-Video/OpenVideoCall-Windows/OpenVideoCall/video_preprocessing_plugin.h deleted file mode 100644 index 303816d9..00000000 --- a/Group-Video/OpenVideoCall-Windows/OpenVideoCall/video_preprocessing_plugin.h +++ /dev/null @@ -1,10 +0,0 @@ - -#ifndef _VIDEO_PREPROCESSING_PLUGIN_H_ -#define _VIDEO_PREPROCESSING_PLUGIN_H_ - -#include - -int load_preprocessing_plugin(agora::rtc::IRtcEngine* engine); -int unload_preprocessing_plugin(agora::rtc::IRtcEngine* engine); - -#endif //_VIDEO_PREPROCESSING_PLUGIN_H_ diff --git a/Group-Video/OpenVideoCall-Windows/README.md b/Group-Video/OpenVideoCall-Windows/README.md index 60eb5336..5329957b 100644 --- a/Group-Video/OpenVideoCall-Windows/README.md +++ b/Group-Video/OpenVideoCall-Windows/README.md @@ -65,13 +65,9 @@ please select the OpenVideoCall project in the Solution Explorer and right click Tips: The relevant dll library has been configured for you in this case tutorial. If you want to use the interface provided by agora for related development, you need to put the dll library into the corresponding execution path as prompted above. ## Resources -- For potential issues, you may take a look at our [FAQ](https://docs.agora.io/en/faq) first -- Dive into [Agora SDK Samples](https://github.com/AgoraIO) to see more tutorials -- Would like to see how Agora SDK is used in more complicated real use case? Take a look at [Agora Use Case](https://github.com/AgoraIO-usecase) -- Repositories managed by developer communities can be found at [Agora Community](https://github.com/AgoraIO-Community) + - You can find full API document at [Document Center](https://docs.agora.io/en/) -- If you encounter problems during integration, you can ask question in [Developer Forum](https://stackoverflow.com/questions/tagged/agora.io/) -- You can file bugs about this sample at [issue](https://github.com/AgoraIO/Basic-Video-Call/issues) +- You can file bugs about this demo at [issue](https://github.com/AgoraIO/Basic-Video-Call/issues) ## License diff --git a/Group-Video/OpenVideoCall-Windows/README.zh.md b/Group-Video/OpenVideoCall-Windows/README.zh.md index 64b6c13a..47a23eae 100644 --- a/Group-Video/OpenVideoCall-Windows/README.zh.md +++ b/Group-Video/OpenVideoCall-Windows/README.zh.md @@ -63,13 +63,11 @@ Agora 视频 SDK 支持 iOS / Android / Windows / macOS 等多个平台,你可 ## 联系我们 -- 如果你遇到了困难,可以先参阅[常见问题](https://docs.agora.io/cn/faq) -- 如果你想了解更多官方示例,可以参考[官方SDK示例](https://github.com/AgoraIO) -- 如果你想了解声网SDK在复杂场景下的应用,可以参考[官方场景案例](https://github.com/AgoraIO-usecase) -- 如果你想了解声网的一些社区开发者维护的项目,可以查看[社区](https://github.com/AgoraIO-Community) - 完整的 API 文档见 [文档中心](https://docs.agora.io/cn/) -- 若遇到问题需要开发者帮助,你可以到 [开发者社区](https://rtcdeveloper.com/) 提问 -- 如果发现了示例代码的 bug,欢迎提交 [issue](https://github.com/AgoraIO/Basic-Video-Call/issues) +- 如果在集成中遇到问题, 你可以到 [开发者社区](https://dev.agora.io/cn/) 提问 +- 如果有售前咨询问题, 可以拨打 400 632 6626,或加入官方Q群 12742516 提问 +- 如果需要售后技术支持, 你可以在 [Agora Dashboard](https://dashboard.agora.io) 提交工单 +- 如果发现了示例代码的 bug, 欢迎提交 [issue](https://github.com/AgoraIO/Basic-Video-Call/issues) ## 代码许可 diff --git a/Group-Video/OpenVideoCall-Windows/agoraconfig.cpp b/Group-Video/OpenVideoCall-Windows/agoraconfig.cpp new file mode 100644 index 00000000..309677a3 --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/agoraconfig.cpp @@ -0,0 +1,97 @@ +#include "agoraconfig.h" + +CAgoraConfig::CAgoraConfig() +{ + m_spConfig = std::make_shared("AgoraConfigOpenVideoCall.ini",QSettings::IniFormat); +} + +void CAgoraConfig::setAppId(const QString &str) +{ + return m_spConfig->setValue("/BaseInfo/AppId",str); +} + +QString CAgoraConfig::getAppId() +{ + return m_spConfig->value("/BaseInfo/AppId").toString(); +} + +void CAgoraConfig::setChannelName(const QString &str) +{ + return m_spConfig->setValue("/BaseInfo/CameraName",str); +} + +QString CAgoraConfig::getChannelName() +{ + return m_spConfig->value("/BaseInfo/ChannelName").toString(); +} + +void CAgoraConfig::setEnableVideo(bool bEnable) +{ + return m_spConfig->setValue("/BaseInfo/EnableVideo",bEnable); +} + +bool CAgoraConfig::getEnableVideo() +{ + return m_spConfig->value("/BaseInfo/EnableVideo").toBool(); +} + +void CAgoraConfig::setEnableAudio(bool bEnable) +{ + return m_spConfig->setValue("/BaseInfo/EnableAudio",bEnable); +} + +bool CAgoraConfig::getEnableAudio() +{ + return m_spConfig->value("/BaseInfo/EnableAudio").toBool(); +} + + +void CAgoraConfig::setEnableBeauty(bool bEnable) +{ + return m_spConfig->setValue("/BaseInfo/EnableBeauty", bEnable); +} + +bool CAgoraConfig::getEnableBeauty() +{ + return m_spConfig->value("/BaseInfo/EnableBeauty").toBool(); +} + +void CAgoraConfig::setLigtheningContrastLevel(int level) +{ + return m_spConfig->setValue("/Beauty/LightengingContrastLevel", level); +} + +int CAgoraConfig::getLigtheningContrastLevel() +{ + return m_spConfig->value("/Beauty/LightengingContrastLevel").toInt(); +} + +void CAgoraConfig::setRedness(int level) +{ + return m_spConfig->setValue("/Beauty/Redness", level); +} + +int CAgoraConfig::getRedness() +{ + return m_spConfig->value("/Beauty/Redness").toInt(); +} + +void CAgoraConfig::setLightenging(int lightening) +{ + return m_spConfig->setValue("/Beauty/Lightening", lightening); +} + +int CAgoraConfig::getLightenging() +{ + return m_spConfig->value("/Beauty/Lightening").toInt(); +} + +void CAgoraConfig::setSmoothness(int smooth) +{ + return m_spConfig->setValue("/Beauty/Smoothness", smooth); +} + +int CAgoraConfig::getSmoothness() +{ + return m_spConfig->value("/Beauty/Smoothness").toInt(); +} \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Windows/agoraconfig.h b/Group-Video/OpenVideoCall-Windows/agoraconfig.h new file mode 100644 index 00000000..2eca306f --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/agoraconfig.h @@ -0,0 +1,39 @@ +#ifndef CAGORACONFIG_H +#define CAGORACONFIG_H +#include +#include + +class CAgoraConfig +{ +public: + CAgoraConfig(); + + void setAppId(const QString &str); + QString getAppId(); + void setChannelName(const QString &str); + QString getChannelName(); + void setEnableVideo(bool bEnable); + bool getEnableVideo(); + void setEnableAudio(bool bEnable); + bool getEnableAudio(); + + + void setEnableBeauty(bool bEnable); + bool getEnableBeauty(); + + void setLigtheningContrastLevel(int level); + int getLigtheningContrastLevel(); + + void setRedness(int level); + int getRedness(); + + void setLightenging(int lightening); + int getLightenging(); + + void setSmoothness(int smooth); + int getSmoothness(); +private: + std::shared_ptr m_spConfig; +}; + +#endif // CAGORACONFIG_H diff --git a/Group-Video/OpenVideoCall-Windows/agoraobject.cpp b/Group-Video/OpenVideoCall-Windows/agoraobject.cpp new file mode 100644 index 00000000..4b0209c7 --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/agoraobject.cpp @@ -0,0 +1,465 @@ +#include "agoraobject.h" +#include +#include + +CAgoraConfig gAgoraConfig; + +class AgoraRtcEngineEvent : public agora::rtc::IRtcEngineEventHandler +{ + CAgoraObject& m_pInstance; +public: + AgoraRtcEngineEvent(CAgoraObject& engine) + :m_pInstance(engine) + {} + + virtual void onVideoStopped() override + { + emit m_pInstance.sender_videoStopped(); + } + virtual void onJoinChannelSuccess(const char* channel, uid_t uid, int elapsed) override + { + emit m_pInstance.sender_joinedChannelSuccess(QString(channel),uid,elapsed); + } + virtual void onUserJoined(uid_t uid, int elapsed) override + { + //qDebug("%s %u",__FUNCTION__,uid); + emit m_pInstance.sender_userJoined(uid, elapsed); + } + virtual void onUserOffline(uid_t uid, USER_OFFLINE_REASON_TYPE reason) override + { + emit m_pInstance.sender_userOffline(uid, reason); + } + virtual void onFirstLocalVideoFrame(int width, int height, int elapsed) override + { + emit m_pInstance.sender_firstLocalVideoFrame(width, height, elapsed); + } + virtual void onFirstRemoteVideoDecoded(uid_t uid, int width, int height, int elapsed) override + { + emit m_pInstance.sender_firstRemoteVideoDecoded(uid, width, height, elapsed); + } + virtual void onFirstRemoteVideoFrame(uid_t uid, int width, int height, int elapsed) override + { + emit m_pInstance.sender_firstRemoteVideoFrameDrawn(uid, width, height, elapsed); + } + virtual void onLocalVideoStats(const LocalVideoStats &stats) override + { + emit m_pInstance.sender_localVideoStats(stats); + } + virtual void onRemoteVideoStats(const RemoteVideoStats &stats) override + { + emit m_pInstance.sender_remoteVideoStats(stats); + } + virtual void onRtcStats(const RtcStats &stats) override + { + emit m_pInstance.sender_rtcStats(stats); + } + virtual void onLastmileQuality(int quality) override + { + emit m_pInstance.sender_lastmileQuality(quality); + } + virtual void onLastmileProbeResult(const LastmileProbeResult &result) override + { + emit m_pInstance.sender_lastmileProbeResult(result); + } +}; + +CAgoraObject* CAgoraObject::getInstance(QObject *parent) +{ + std::lock_guard autoLock(m_mutex); + if(nullptr == m_pInstance) + m_pInstance = new CAgoraObject(parent); + + return m_pInstance; +} + +CAgoraObject* CAgoraObject::m_pInstance = nullptr; +std::mutex CAgoraObject::m_mutex; + +CAgoraObject::CAgoraObject(QObject *parent): + QObject(parent), + m_rtcEngine(createAgoraRtcEngine()), + m_eventHandler(new AgoraRtcEngineEvent(*this)) +{ + agora::rtc::RtcEngineContext context; + context.eventHandler = m_eventHandler.get(); + QByteArray temp; + if(strlen(APPID)) + context.appId = APPID; + else { + QString strAppId = gAgoraConfig.getAppId(); + temp = strAppId.toUtf8(); + context.appId = const_cast(temp.data()); + } + if (*context.appId == '\0') + { + QMessageBox::critical(nullptr, ("AgoraOpenLive"), + ("You must specify APP ID before using the demo")); + } + m_rtcEngine->initialize(context); +} + +CAgoraObject::~CAgoraObject() +{ + if(m_rtcEngine) + m_rtcEngine->release(); +} + +int CAgoraObject::joinChannel(const QString& key, const QString& channel, uint uid) +{ + if (channel.isEmpty()) { + QMessageBox::warning(nullptr,("AgoraHighSound"),("channelname is empty")); + return -1; + } + + m_rtcEngine->startPreview(); + int r = m_rtcEngine->joinChannel(key.toUtf8().data(), channel.toUtf8().data(), nullptr, uid); + + return r; +} + +int CAgoraObject::leaveChannel() +{ + m_rtcEngine->stopPreview(); + int r = m_rtcEngine->leaveChannel(); + return r; +} + +int CAgoraObject::muteLocalAudioStream(bool muted) +{ + RtcEngineParameters rep(*m_rtcEngine); + return rep.muteLocalAudioStream(muted); +} + +BOOL CAgoraObject::LocalVideoPreview(HWND hVideoWnd, BOOL bPreviewOn, RENDER_MODE_TYPE renderType/* = RENDER_MODE_TYPE::RENDER_MODE_FIT*/) +{ + int nRet = 0; + + if (bPreviewOn) { + VideoCanvas vc; + + vc.uid = 0; + vc.view = hVideoWnd; + vc.renderMode = renderType; + + m_rtcEngine->setupLocalVideo(vc); + nRet = m_rtcEngine->startPreview(); + } + else + nRet = m_rtcEngine->stopPreview(); + + return nRet == 0 ? TRUE : FALSE; +} + +BOOL CAgoraObject::RemoteVideoRender(uid_t uid, HWND hVideoWnd, RENDER_MODE_TYPE renderType/* = RENDER_MODE_TYPE::RENDER_MODE_HIDDEN*/) +{ + int nRet = 0; + + VideoCanvas vc; + + vc.uid = uid; + vc.view = hVideoWnd; + vc.renderMode = renderType; + + m_rtcEngine->setupRemoteVideo(vc); + + return nRet == 0 ? TRUE : FALSE; +} + +BOOL CAgoraObject::startLastMileProbeTest(bool enable) +{ + int nres = 0; + if(enable) { + LastmileProbeConfig lp; + lp.probeUplink =true; + lp.probeDownlink = true; + lp.expectedDownlinkBitrate = 5000; + lp.expectedUplinkBitrate = 5000; + + nres = m_rtcEngine->startLastmileProbeTest(lp); + } + else { + nres = m_rtcEngine->stopLastmileProbeTest(); + } + + return nres == 0? TRUE : FALSE; +} + +int CAgoraObject::enableVideo(bool enabled) +{ + return enabled ? m_rtcEngine->enableVideo() : m_rtcEngine->disableVideo(); +} + +int CAgoraObject::enableAudio(bool enabled) +{ + return enabled ? m_rtcEngine->enableAudio() : m_rtcEngine->disableAudio(); +} + +BOOL CAgoraObject::setLogPath(const QString &strDir) +{ + int ret = 0; + + RtcEngineParameters rep(*m_rtcEngine); + ret = rep.setLogFile(strDir.toUtf8().data()); + + return ret == 0 ? TRUE : FALSE; +} + +BOOL CAgoraObject::SetChannelProfile(CHANNEL_PROFILE_TYPE channelType) +{ + int ret = 0; + ret = m_rtcEngine->setChannelProfile(channelType); + + return ret == 0 ? TRUE : FALSE; +} + +BOOL CAgoraObject::SetClientRole(CLIENT_ROLE_TYPE roleType) +{ + int ret = 0; + + ret = m_rtcEngine->setClientRole(roleType); + + return ret == 0 ? TRUE : FALSE; +} + +BOOL CAgoraObject::EnableWebSdkInteroperability(BOOL bEnable) +{ + RtcEngineParameters rep(*m_rtcEngine); + + int nRet = rep.enableWebSdkInteroperability(static_cast(bEnable)); + + return nRet == 0 ? TRUE : FALSE; +} + +qSSMap CAgoraObject::getRecordingDeviceList() +{ + qSSMap devices; + AAudioDeviceManager audioDeviceManager(m_rtcEngine); + if (!audioDeviceManager) + return devices; + + agora::util::AutoPtr spCollection(audioDeviceManager->enumerateRecordingDevices()); + if (!spCollection) + return devices; + char name[MAX_DEVICE_ID_LENGTH], guid[MAX_DEVICE_ID_LENGTH]; + int count = spCollection->getCount(); + if (count > 0) + { + for (int i = 0; i < count; i++) + { + if (!spCollection->getDevice(i, name, guid)) + { + devices[name] = guid; + } + } + } + return devices; +} + +qSSMap CAgoraObject::getPlayoutDeviceList() +{ + qSSMap devices; + AAudioDeviceManager audioDeviceManager(m_rtcEngine); + if (!audioDeviceManager) + return devices; + + agora::util::AutoPtr spCollection(audioDeviceManager->enumeratePlaybackDevices()); + if (!spCollection) + return devices; + char name[MAX_DEVICE_ID_LENGTH], guid[MAX_DEVICE_ID_LENGTH]; + int count = spCollection->getCount(); + if (count > 0) + { + for (int i = 0; i < count; i++) + { + if (!spCollection->getDevice(i, name, guid)) + { + devices[name] = guid; + } + } + } + return devices; +} + +qSSMap CAgoraObject::getVideoDeviceList() +{ + m_rtcEngine->enableVideo(); + qSSMap devices; + AVideoDeviceManager videoDeviceManager(m_rtcEngine); + if (!videoDeviceManager) + return devices; + + agora::util::AutoPtr spCollection(videoDeviceManager->enumerateVideoDevices()); + if (!spCollection) + return devices; + char name[MAX_DEVICE_ID_LENGTH], guid[MAX_DEVICE_ID_LENGTH]; + int count = spCollection->getCount(); + if (count > 0) + { + for (int i = 0; i < count; i++) + { + if (!spCollection->getDevice(i, name, guid)) + { + devices[name] = guid; + } + } + } + return devices; +} + +int CAgoraObject::setRecordingDevice(const QString& guid) +{ + if (guid.isEmpty()) + return -1; + AAudioDeviceManager audioDeviceManager(m_rtcEngine); + if (!audioDeviceManager) + return -1; + return audioDeviceManager->setRecordingDevice(guid.toUtf8().data()); +} + +int CAgoraObject::setPlayoutDevice(const QString& guid) +{ + if (guid.isEmpty()) + return -1; + AAudioDeviceManager audioDeviceManager(m_rtcEngine); + if (!audioDeviceManager) + return -1; + return audioDeviceManager->setPlaybackDevice(guid.toUtf8().data()); +} + +int CAgoraObject::setVideoDevice(const QString& guid) +{ + if (guid.isEmpty()) + return -1; + AVideoDeviceManager videoDeviceManager(m_rtcEngine); + if (!videoDeviceManager) + return -1; + return videoDeviceManager->setDevice(guid.toUtf8().data()); +} + +BOOL CAgoraObject::setVideoProfile(int nWidth,int nHeight) +{ + int res = 0; + VideoEncoderConfiguration vec; + vec = VideoEncoderConfiguration(nWidth,nHeight,FRAME_RATE_FPS_15,500,ORIENTATION_MODE_FIXED_LANDSCAPE); + res = m_rtcEngine->setVideoEncoderConfiguration(vec); + + return res ==0 ? TRUE : FALSE; +} + +BOOL CAgoraObject::setRecordingIndex(int nIndex) +{ + int res = 0; + AAudioDeviceManager audioDeviceManager(m_rtcEngine); + if (!audioDeviceManager) + return FALSE; + + agora::util::AutoPtr spCollection(audioDeviceManager->enumerateRecordingDevices()); + if (!spCollection) + return FALSE; + char name[MAX_DEVICE_ID_LENGTH], guid[MAX_DEVICE_ID_LENGTH]; + int count = spCollection->getCount(); + assert(res < count); + spCollection->getDevice(nIndex,name,guid); + res = spCollection->setDevice(guid); + + return res ==0 ? TRUE:FALSE; +} + +BOOL CAgoraObject::setPlayoutIndex(int nIndex) +{ + int res = 0; + AAudioDeviceManager audioDeviceManager(m_rtcEngine); + if (!audioDeviceManager) + return FALSE; + + agora::util::AutoPtr spCollection(audioDeviceManager->enumeratePlaybackDevices()); + if (!spCollection) + return FALSE; + char name[MAX_DEVICE_ID_LENGTH], guid[MAX_DEVICE_ID_LENGTH]; + int count = spCollection->getCount(); + assert(res < count); + spCollection->getDevice(nIndex,name,guid); + res = spCollection->setDevice(guid); + + return res ==0 ? TRUE:FALSE; +} + +BOOL CAgoraObject::setVideoIndex(int nIndex) +{ + + int res = 0; + AVideoDeviceManager videoDeviceManager(m_rtcEngine); + if (!videoDeviceManager) + return FALSE; + + agora::util::AutoPtr spCollection(videoDeviceManager->enumerateVideoDevices()); + if (!spCollection) + return FALSE; + char name[MAX_DEVICE_ID_LENGTH], guid[MAX_DEVICE_ID_LENGTH]; + int count = spCollection->getCount(); + assert(nIndex < count); + spCollection->getDevice(nIndex,name,guid); + res = spCollection->setDevice(guid); + + return res == 0 ? TRUE : FALSE; +} + +BOOL CAgoraObject::MuteLocalVideo(BOOL bMute) +{ + int nRet = 0; + + RtcEngineParameters rep(*m_rtcEngine); + nRet = rep.enableLocalVideo(!bMute); + + return nRet == 0 ? TRUE : FALSE; +} + +BOOL CAgoraObject::MuteLocalAudio(BOOL bMute) +{ + int nRet = 0; + + RtcEngineParameters rep(*m_rtcEngine); + nRet = m_rtcEngine->enableLocalAudio(!bMute); + + return nRet == 0 ? TRUE : FALSE; +} + +BOOL CAgoraObject::SetEncryptionMode(const char* secret,const char* secretMode) +{ + int nRet = 0; + if(secret != nullptr && strlen(secret) > 0 && secretMode != nullptr) { + nRet = m_rtcEngine->setEncryptionSecret(secret); + nRet = m_rtcEngine->setEncryptionMode(secretMode); + } + + return nRet == 0 ? TRUE : FALSE; +} + +BOOL CAgoraObject::SetLogFilter(LOG_FILTER_TYPE logFilterType, LPCTSTR lpLogPath) +{ + int nRet = 0; + RtcEngineParameters rep(*m_rtcEngine); + + nRet = rep.setLogFilter(logFilterType); + + if (lpLogPath != Q_NULLPTR) { +#ifdef UNICODE + CHAR szFilePath[MAX_PATH]; + ::WideCharToMultiByte(CP_ACP, 0, lpLogPath, -1, szFilePath, MAX_PATH, nullptr, nullptr); + nRet |= rep.setLogFile(szFilePath); +#else + nRet |= rep.setLogFile(lpLogPath); +#endif + } + + return nRet == 0 ? TRUE : FALSE; +} + + +bool CAgoraObject::setBeautyEffectOptions(bool enabled, BeautyOptions& options) +{ + int nRet = 0; + + nRet = m_rtcEngine->setBeautyEffectOptions(enabled, options); + return nRet == 0 ? true : false; +} \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Windows/agoraobject.h b/Group-Video/OpenVideoCall-Windows/agoraobject.h new file mode 100644 index 00000000..5867b5cc --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/agoraobject.h @@ -0,0 +1,89 @@ +#ifndef CAGORAOBJECT_H +#define CAGORAOBJECT_H + +#include +#include + +#include "agoraconfig.h" +extern CAgoraConfig gAgoraConfig; + +//Specify your APP ID here +#define APPID "" +#define APP_TOKEN "" + +#include +#include +#include +#include +#include +using namespace agora; +using namespace agora::rtc; + +typedef QMap qSSMap; + +class CAgoraObject:public QObject +{ + Q_OBJECT +public: + + int joinChannel(const QString& key, const QString& channel, uint uid); + int leaveChannel(); + int muteLocalAudioStream(bool muted); + BOOL LocalVideoPreview(HWND hVideoWnd, BOOL bPreviewOn, RENDER_MODE_TYPE renderType = RENDER_MODE_TYPE::RENDER_MODE_FIT); + BOOL RemoteVideoRender(uid_t uid, HWND hVideoWnd, RENDER_MODE_TYPE renderType = RENDER_MODE_TYPE::RENDER_MODE_HIDDEN); + + BOOL startLastMileProbeTest(bool enable); + int enableVideo(bool enabled); + int enableAudio(bool enabled); + BOOL MuteLocalVideo(BOOL bMute); + BOOL MuteLocalAudio(BOOL bMute); + BOOL SetEncryptionMode(const char* secret,const char* secretMode); + + BOOL setLogPath(const QString &strDir); + BOOL SetChannelProfile(CHANNEL_PROFILE_TYPE channelType); + BOOL SetClientRole(CLIENT_ROLE_TYPE roleType); + BOOL EnableWebSdkInteroperability(BOOL bEnable); + + qSSMap getRecordingDeviceList(); + qSSMap getPlayoutDeviceList(); + qSSMap getVideoDeviceList(); + + int setRecordingDevice(const QString& guid); + int setPlayoutDevice(const QString& guid); + int setVideoDevice(const QString& guid); + + BOOL setVideoProfile(int nWidth,int nHeight); + BOOL setRecordingIndex(int nIndex); + BOOL setPlayoutIndex(int nIndex); + BOOL setVideoIndex(int nIndex); + BOOL SetLogFilter(LOG_FILTER_TYPE logFilterType, LPCTSTR lpLogPath); + + bool setBeautyEffectOptions(bool enabled, BeautyOptions& options); +signals: + void sender_videoStopped(); + void sender_joinedChannelSuccess(const QString &qsChannel, unsigned int uid, int elapsed); + void sender_userJoined(unsigned int uid, int elapsed); + void sender_userOffline(unsigned int uid, USER_OFFLINE_REASON_TYPE reason); + void sender_firstLocalVideoFrame(int width, int height, int elapsed); + void sender_firstRemoteVideoDecoded(unsigned int uid, int width, int height, int elapsed); + void sender_firstRemoteVideoFrameDrawn(unsigned int uid, int width, int height, int elapsed); + void sender_localVideoStats(const LocalVideoStats &stats); + void sender_remoteVideoStats(const RemoteVideoStats &stats); + void sender_rtcStats(const RtcStats &stats); + void sender_lastmileQuality(int quality); + void sender_lastmileProbeResult(const LastmileProbeResult &result); + +public: + static CAgoraObject* getInstance(QObject *parent = 0); + static CAgoraObject* m_pInstance; + static std::mutex m_mutex; + +private: + explicit CAgoraObject(QObject *parent = 0); + ~CAgoraObject(); + + agora::rtc::IRtcEngine* m_rtcEngine; + std::unique_ptr m_eventHandler; +}; + +#endif // CAGORAOBJECT_H diff --git a/Group-Video/OpenVideoCall-Windows/agorawindowmanager.cpp b/Group-Video/OpenVideoCall-Windows/agorawindowmanager.cpp new file mode 100644 index 00000000..b521b584 --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/agorawindowmanager.cpp @@ -0,0 +1,47 @@ +#include "agorawindowmanager.h" + +AgoraWindowManager* AgoraWindowManager::m_pInstance = Q_NULLPTR; +std::mutex AgoraWindowManager::m_mutexMgr; + +AgoraWindowManager* AgoraWindowManager::getInstance() +{ + std::lock_guard autolock(m_mutexMgr); + if(Q_NULLPTR == m_pInstance) + m_pInstance = new AgoraWindowManager; + + return m_pInstance; +} + +void AgoraWindowManager::releaseInstance() +{ + std::lock_guard autoLock(m_mutexMgr); + if(Q_NULLPTR != m_pInstance) + delete m_pInstance; + + m_pInstance = Q_NULLPTR; +} + +AgoraWindowManager::AgoraWindowManager() +{ + +} + +AgoraWindowManager::~AgoraWindowManager() +{ +} + +void AgoraWindowManager::insertItem(eQMainWndType type,QMainWindow* pWnd) +{ + std::lock_guard autolock(m_mutexMgr); + m_qmapeq[type] = pWnd; +} + +QMainWindow* AgoraWindowManager::getQWnd(eQMainWndType type) +{ + std::lock_guard autolock(m_mutexMgr); + QMainWindow* pWndTemp = Q_NULLPTR; + if(m_qmapeq.contains(type)) + pWndTemp = m_qmapeq.value(type); + + return pWndTemp; +} diff --git a/Group-Video/OpenVideoCall-Windows/agorawindowmanager.h b/Group-Video/OpenVideoCall-Windows/agorawindowmanager.h new file mode 100644 index 00000000..f9663a03 --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/agorawindowmanager.h @@ -0,0 +1,38 @@ +#ifndef AGORAWINDOWMANAGER_H +#define AGORAWINDOWMANAGER_H + +#include +#include +#include + +enum eQMainWndType { + qWndType_NULL = -1, + qWndType_OpenVideoCall, + qWndType_AvDevice, + qWndType_NetTesting, + qWndType_NetTestResult, + qWndType_NetTestDetail, + qWndType_InRoom, + qWndType_EnterRoom, + + qWndType_UNKNOWN = 0xff, +}; + +typedef QMap qMapeq; +class AgoraWindowManager +{ +public: + static AgoraWindowManager* getInstance(); + static void releaseInstance(); + void insertItem(eQMainWndType type,QMainWindow* pWnd); + QMainWindow* getQWnd(eQMainWndType type); + +private: + AgoraWindowManager(); + ~AgoraWindowManager(); + static AgoraWindowManager* m_pInstance; + qMapeq m_qmapeq; + static std::mutex m_mutexMgr; +}; + +#endif // AGORAWINDOWMANAGER_H diff --git a/Group-Video/OpenVideoCall-Windows/avdevice.cpp b/Group-Video/OpenVideoCall-Windows/avdevice.cpp new file mode 100644 index 00000000..d8581b00 --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/avdevice.cpp @@ -0,0 +1,395 @@ +#include "avdevice.h" +#include "ui_avdevice.h" +#include "agoraobject.h" +#include "agorawindowmanager.h" +#include +AVDevice::AVDevice(QMainWindow* pLastWnd,const QString &qsChanne,QWidget *parent) : + QMainWindow(parent), + m_lastWnd(pLastWnd), + ui(new Ui::AVDevice), + m_bEnableAudio(true), + m_bEnableVideo(true), + m_bEnableBeauty(false), + m_strChannel(qsChanne) +{ + ui->setupUi(this); + ui->scrollArea->verticalScrollBar()->setStyleSheet(QLatin1String("" + "QScrollBar:vertical {border: none;background-color: rgb(255,255,255);width: 10px;margin: 0px 0 0px 0;}" + " QScrollBar::handle:vertical { background: rgba(240, 240, 240, 255); min-height: 20px;width: 6px;border: 1px solid rgba(240, 240, 240, 255);border-radius: 3px;margin-left:2px;margin-right:2px;}" + " QScrollBar::add-line:vertical {background-color: rgb(255,255,255);height: 4px;}" + " QScrollBar::sub-line:vertical {background-color: rgb(255,255,255);height: 4px;}" + " QScrollBar::up-arrow:vertical, QScrollBar::down-arrow:vertical {height: 0px;}" + " QScrollBar::add-page:vertical, QScrollBar::sub-page:vertical {background: none;}")); + + m_bEnableBeauty = gAgoraConfig.getEnableBeauty(); + m_bEnableAudio = gAgoraConfig.getEnableAudio(); + m_bEnableVideo = gAgoraConfig.getEnableVideo(); + connect(ui->horizontalSlider_Redness, &QSlider::valueChanged, this, &AVDevice::on_valueChanged_horizontalSlider_Redness); + connect(ui->horizontalSlider_Smoothness, &QSlider::valueChanged, this, &AVDevice::on_valueChanged_horizontalSlider_Smoothness); + connect(ui->horizontalSliderLightening, &QSlider::valueChanged, this, &AVDevice::on_valueChanged_horizontalSlider_Lightening); + + this->setWindowFlags(Qt::FramelessWindowHint | Qt::WindowSystemMenuHint); + this->setAttribute(Qt::WA_TranslucentBackground); + + initCtrl(); + + AgoraWindowManager::getInstance()->insertItem(qWndType_AvDevice,this); +} + +AVDevice::~AVDevice() +{ + delete ui; +} + +void AVDevice::mousePressEvent(QMouseEvent *e) +{ + if(e->button() == Qt::LeftButton) { + m_mousePosition = e->pos(); + if(m_mousePosition.x() < lnTitleWidth && + m_mousePosition.x() >= lnGapWidth && + m_mousePosition.y() >= lnGapHeight && + m_mousePosition.y() < lnTitleHeight) + m_bMousePressed = true; + } +} + +void AVDevice::mouseMoveEvent(QMouseEvent *e) +{ + if(m_bMousePressed == true) { + QPoint movePos = e->globalPos() - m_mousePosition; + move(movePos); + e->accept(); + } +} + +void AVDevice::mouseReleaseEvent(QMouseEvent *e) +{ + m_bMousePressed = false; +} + +void AVDevice::initCtrl() +{ + ui->lb_channel->setText(m_strChannel); + setStyleSheet_audio(m_bEnableAudio); + setStyleSheet_video(m_bEnableVideo); + + //videoProfile + ui->cb_solution->clear(); + ui->cb_solution->addItem("160x120"); + ui->cb_solution->addItem("320x180"); + ui->cb_solution->addItem("320x240"); + ui->cb_solution->addItem("640x360"); + ui->cb_solution->addItem("640x480"); + ui->cb_solution->addItem("1280x720"); + ui->cb_solution->addItem("1920x1080"); + ui->cb_solution->addItem("3840x2160"); + ui->cb_solution->setCurrentIndex(3); + + //microphone. + ui->cb_audio->clear(); + QString qDeviceName; + qSSMap devicelist = CAgoraObject::getInstance()->getRecordingDeviceList(); + for (qSSMap::iterator it = devicelist.begin(); devicelist.end() != it; it++) { + ui->cb_audio->addItem(it.key()); + } + + //playout. + ui->cb_speaker->clear(); + devicelist.clear(); + devicelist = CAgoraObject::getInstance()->getPlayoutDeviceList(); + for(qSSMap::iterator it = devicelist.begin(); devicelist.end() != it; it++) { + ui->cb_speaker->addItem(it.key()); + } + + //cameralist + ui->cb_video->clear(); + devicelist.clear(); + devicelist = CAgoraObject::getInstance()->getVideoDeviceList(); + for(qSSMap::iterator it = devicelist.begin(); devicelist.end() != it; it++) { + ui->cb_video->addItem(it.key()); + } + + //log filter + ui->cb_log->clear(); + ui->cb_log->addItem("OFF"); + ui->cb_log->addItem("DEBUG"); + ui->cb_log->addItem("INFO"); + ui->cb_log->addItem("WARN"); + ui->cb_log->addItem("ERROR"); + ui->cb_log->addItem("CRITICAL"); + ui->cb_log->addItem("MASK"); + ui->cb_log->setCurrentIndex(2); + + m_bEnableBeauty = gAgoraConfig.getEnableBeauty(); + + if (!m_bEnableBeauty) { + QString str = "QPushButton:!hover {\ + border-image: url(:/uiresource/switch-off.png);\ + background-image: url(:/uiresource/switch-off.png);\ + }\ + \ + QPushButton:hover {\ + border-image: url(:/uiresource/switch-off.png);\ + background-image: url(:/uiresource/switch-off.png);\ + }"; + + ui->optVideo_Beauty->setStyleSheet(str); + } + else { + QString str = "QPushButton:!hover {\ + border-image: url(:/uiresource/switch-open.png);\ + background-image: url(:/uiresource/switch-open.png);\ + }\ + \ + QPushButton:hover {\ + border-image: url(:/uiresource/switch-open.png);\ + background-image: url(:/uiresource/switch-open.png);\ + }"; + + ui->optVideo_Beauty->setStyleSheet(str); + } + //beauty + ui->cbContrastLevel->clear(); + ui->cbContrastLevel->addItem(QString("Lightening Contrast Low")); + ui->cbContrastLevel->addItem(QString("Lightening Contrast Normal")); + ui->cbContrastLevel->addItem(QString("Lightening Contrast High")); + + ui->cbContrastLevel->setCurrentIndex(gAgoraConfig.getLigtheningContrastLevel()); + + ui->horizontalSlider_Redness->setValue(gAgoraConfig.getRedness()); + ui->horizontalSliderLightening->setValue(gAgoraConfig.getLightenging()); + ui->horizontalSlider_Smoothness->setValue(gAgoraConfig.getSmoothness()); +} + + +void AVDevice::setStyleSheet_audio(bool bEnable) +{ + QString qsStyle ; + if(bEnable) { + qsStyle = "QPushButton:!pressed {\ + width:50px;\ + height:30px;\ + border-radius:19px;\ + image: url(:/uiresource/switch-open.png)\ + }" \ + "QPushButton:pressed {\ + width:50px;\ + height:30px;\ + border-radius:19px;\ + image: url(:/uiresource/switch-open.png)\ + }"; + } + else { + qsStyle = "QPushButton:!pressed {\ + width:50px;\ + height:30px;\ + border-radius:19px;\ + image: url(:/uiresource/switch-off.png)\ + }"\ + "QPushButton:pressed {\ + width:50px;\ + height:30px;\ + border-radius:19px;\ + image: url(:/uiresource/switch-off.png)\ + }"; + + } + + ui->btn_audio->setStyleSheet(qsStyle); +} + +void AVDevice::setStyleSheet_video(bool bEnable) +{ + QString qsStyle; + if(bEnable) { + qsStyle = "QPushButton:!pressed {\ + width:50px;\ + height:30px;\ + border-radius:19px;\ + image: url(:/uiresource/switch-open.png)\ + }"\ + "QPushButton:pressed {\ + width:50px;\ + height:30px;\ + border-radius:19px;\ + image: url(:/uiresource/switch-open.png)\ + }"; + } + else { + qsStyle = "QPushButton:!pressed {\ + width:50px;\ + height:30px;\ + border-radius:19px;\ + image: url(:/uiresource/switch-off.png)\ + }"\ + "QPushButton:pressed {\ + width:50px;\ + height:30px;\ + border-radius:19px;\ + image: url(:/uiresource/switch-off.png)\ + }"; + } + ui->btn_video->setStyleSheet(qsStyle); +} + + +void AVDevice::enableVideoBeutyControl(bool bEnable) +{ + ui->cbContrastLevel->setDisabled(bEnable); + ui->horizontalSliderLightening->setDisabled(bEnable); + ui->horizontalSlider_Redness->setDisabled(bEnable); + ui->horizontalSlider_Smoothness->setDisabled(bEnable); +} + +void AVDevice::on_optVideo_Beauty_clicked() +{ + m_bEnableBeauty = !m_bEnableBeauty; + enableVideoBeutyControl(!m_bEnableBeauty); + updateBeautyOptions(); + if (!m_bEnableBeauty) { + QString str = "QPushButton:!hover {\ + border-image: url(:/uiresource/switch-off.png);\ + background-image: url(:/uiresource/switch-off.png);\ + }\ + \ + QPushButton:hover {\ + border-image: url(:/uiresource/switch-off.png);\ + background-image: url(:/uiresource/switch-off.png);\ + }"; + + ui->optVideo_Beauty->setStyleSheet(str); + + } + else { + QString str = "QPushButton:!hover {\ + border-image: url(:/uiresource/switch-open.png);\ + background-image: url(:/uiresource/switch-open.png);\ + }\ + \ + QPushButton:hover {\ + border-image: url(:/uiresource/switch-open.png);\ + background-image: url(:/uiresource/switch-open.png);\ + }"; + + ui->optVideo_Beauty->setStyleSheet(str); + } + + gAgoraConfig.setEnableBeauty(m_bEnableBeauty); +} + +void AVDevice::on_btn_back_clicked() +{ + if(m_lastWnd) + m_lastWnd->show(); + this->hide(); +} + +void AVDevice::on_cb_solution_activated(int index) +{ +} + +void AVDevice::on_cb_audio_activated(int index) +{ + CAgoraObject::getInstance()->setRecordingIndex(index); +} + +void AVDevice::on_cb_video_activated(int index) +{ + CAgoraObject::getInstance()->setVideoIndex(index); +} + +void AVDevice::on_cb_speaker_activated(int index) +{ + CAgoraObject::getInstance()->setPlayoutIndex(index); +} + +void AVDevice::on_btn_audio_clicked() +{ + m_bEnableAudio = !m_bEnableAudio; + setStyleSheet_audio(m_bEnableAudio); + gAgoraConfig.setEnableAudio(m_bEnableAudio); +} + +void AVDevice::on_btn_video_clicked() +{ + m_bEnableVideo = !m_bEnableVideo; + setStyleSheet_video(m_bEnableVideo); + gAgoraConfig.setEnableVideo(m_bEnableVideo); +} + +void AVDevice::on_btn_close_clicked() +{ + on_btn_back_clicked(); +} + +void AVDevice::on_btn_min_clicked() +{ + this->showMinimized(); +} + +void AVDevice::on_cb_solution_activated(const QString &arg1) +{ + int nWidth,nHeight = 0; + sscanf(arg1.toUtf8().data(),"%dx%d", &nWidth, &nHeight); + CAgoraObject::getInstance()->setVideoProfile(nWidth, nHeight); +} + +void AVDevice::on_cb_log_activated(int index) +{ + LOG_FILTER_TYPE logFilterType = LOG_FILTER_OFF; + switch (index) + { + case 0:logFilterType = LOG_FILTER_OFF; break; + case 1:logFilterType = LOG_FILTER_DEBUG;break; + case 2:logFilterType = LOG_FILTER_INFO; break; + case 3:logFilterType = LOG_FILTER_WARN; break; + case 4:logFilterType = LOG_FILTER_ERROR; break; + case 5:logFilterType = LOG_FILTER_CRITICAL; break; + case 6:logFilterType = LOG_FILTER_MASK; break; + default:break; + } + CAgoraObject::getInstance()->SetLogFilter(logFilterType,L""); +} + +void AVDevice::updateBeautyOptions() +{ + BeautyOptions options; + options.lighteningContrastLevel = (BeautyOptions::LIGHTENING_CONTRAST_LEVEL)ui->cbContrastLevel->currentIndex(); + options.lighteningLevel = ui->horizontalSliderLightening->value() / 100.0f; + options.rednessLevel = ui->horizontalSlider_Redness->value() / 100.0f; + options.smoothnessLevel = ui->horizontalSlider_Smoothness->value() / 100.0f; + + CAgoraObject::getInstance()->setBeautyEffectOptions(m_bEnableBeauty, options); +} + +void AVDevice::on_cbContrastLevel_activated(int index) +{ + updateBeautyOptions(); +} + +void AVDevice::on_valueChanged_horizontalSlider_Redness(int value) +{ + QString redness; + redness.sprintf("Redness(%.02f)", value / 100.0f); + ui->labelRedness->setText(redness); + gAgoraConfig.setRedness(value); + updateBeautyOptions(); +} + +void AVDevice::on_valueChanged_horizontalSlider_Smoothness(int value) +{ + QString smooth; + smooth.sprintf("Smoothness(%.02f)", value / 100.0f); + ui->labelSmoothness->setText(smooth); + gAgoraConfig.setSmoothness(value); + updateBeautyOptions(); +} + +void AVDevice::on_valueChanged_horizontalSlider_Lightening(int value) +{ + QString lightening; + lightening.sprintf("Lightening(%.02f)", value / 100.0f); + ui->labelLightening->setText(lightening); + gAgoraConfig.setLightenging(value); + updateBeautyOptions(); +} diff --git a/Group-Video/OpenVideoCall-Windows/avdevice.h b/Group-Video/OpenVideoCall-Windows/avdevice.h new file mode 100644 index 00000000..eff6ad9b --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/avdevice.h @@ -0,0 +1,71 @@ +#ifndef AVDEVICE_H +#define AVDEVICE_H + +#include +#include + +namespace Ui { +class AVDevice; +} + +class AVDevice : public QMainWindow +{ + Q_OBJECT + +public: + explicit AVDevice(QMainWindow* pLastWnd,const QString &qsChanne,QWidget *parent = 0); + ~AVDevice(); + +protected: + virtual void mousePressEvent(QMouseEvent *e); + virtual void mouseMoveEvent(QMouseEvent *e); + virtual void mouseReleaseEvent(QMouseEvent *e); + + void initCtrl(); + void setStyleSheet_audio(bool bEnable); + void setStyleSheet_video(bool bEnable); + +private slots: + void on_btn_back_clicked(); + void on_cb_solution_activated(int index); + void on_cb_audio_activated(int index); + void on_cb_video_activated(int index); + void on_cb_speaker_activated(int index); + void on_btn_audio_clicked(); + void on_btn_video_clicked(); + + void on_optVideo_Beauty_clicked(); + + void on_btn_close_clicked(); + + void on_btn_min_clicked(); + + void on_cb_solution_activated(const QString &arg1); + + void on_cb_log_activated(int index); + + void on_cbContrastLevel_activated(int index); + void on_valueChanged_horizontalSlider_Redness(int value); + void on_valueChanged_horizontalSlider_Smoothness(int value); + void on_valueChanged_horizontalSlider_Lightening(int value); +private: + void enableVideoBeutyControl(bool bEnable); + void updateBeautyOptions(); + + const int lnGapWidth = 18; + const int lnGapHeight = 12; + const int lnTitleWidth = 718; + const int lnTitleHeight = 30; + QPoint m_mousePosition; + bool m_bMousePressed; + +private: + Ui::AVDevice *ui; + QMainWindow* m_lastWnd; + QString m_strChannel; + bool m_bEnableVideo; + bool m_bEnableAudio; + bool m_bEnableBeauty; +}; + +#endif // AVDEVICE_H diff --git a/Group-Video/OpenVideoCall-Windows/avdevice.ui b/Group-Video/OpenVideoCall-Windows/avdevice.ui new file mode 100644 index 00000000..84726637 --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/avdevice.ui @@ -0,0 +1,1229 @@ + + + AVDevice + + + + 0 + 0 + 786 + 536 + + + + MainWindow + + + + + + + + + + false + + + QWidget#centralwidget { +image: url(:/uiresource/OVC-win-config.png); +} + + + + + 418 + 25 + 36 + 36 + + + + QPushButton:!hover { +width:36px; +height:36px; +border-image: url(:/uiresource/icon-back.png); +image: url(:/uiresource/icon-back.png); +} +QPushButton:hover{ +width:36px; +height:36px; +border-image: url(:/uiresource/icon-back hover.png); +image: url(:/uiresource/icon-back hover.png); +} + + + + + + + + + 698 + 34 + 18 + 18 + + + + QPushButton:!hover { +image: url(:/uiresource/icon-min default.png); +border-image: url(:/uiresource/icon-min default.png); +} + +QPushButton:hover { +image: url(:/uiresource/icon-min hover.png); +border-image: url(:/uiresource/icon-min hover.png); +} + + + + + + + + + 726 + 34 + 18 + 18 + + + + QPushButton:!hover { +image: url(:/uiresource/icon-close default.png); +border-image: url(:/uiresource/icon-close default.png); +} + +QPushButton:hover { +image: url(:/uiresource/icon-close hover.png); +border-image: url(:/uiresource/icon-close hover.png); +} + + + + + + + + true + + + + 425 + 103 + 317 + 22 + + + + border-image: url(:/uiresource/edit1.png); +font-size:16px; +font-family:HelveticaNeue; +color:rgba(51,51,51,1); +line-height:18px; + + + + + + 410 + 80 + 350 + 426 + + + + QScrollArea{ + background-color: rgb(255, 255, 255); + border:none; +}; + + + QFrame::Plain + + + Qt::ScrollBarAlwaysOff + + + true + + + Qt::AlignLeading|Qt::AlignLeft|Qt::AlignTop + + + + + 0 + -141 + 340 + 567 + + + + background-color: rgb(255, 255, 255); + + + + 4 + + + + + + + QLabel{ +font-family: "Arial"; +font-size: 12px; +color:rgb(144,144,144); +}; + + + Name + + + + + + + + HelveticaNeue + -1 + + + + border-image: url(:/uiresource/edit1.png); +image: url(:/uiresource/edit1.png); +font-size:16px; +font-family:HelveticaNeue; +color:rgba(51,51,51,1); +line-height:18px; + + + + + + + + + + + + + 0 + 1 + + + + + 16777215 + 1 + + + + border-top: 1px solid rgb(234, 234, 234); + + + QFrame::Plain + + + Qt::Horizontal + + + + + + + + + QLabel{ +font-family: "Arial"; +font-size: 12px; +color:rgb(144,144,144); +}; + + + Resolution + + + + + + + + 微软雅黑 + -1 + + + + QComboBox { +font-family: "微软雅黑"; +font-size: 13px; +padding: 3px 0x 3px 5px; +border-image: url(:/uiresource/box-01.png); +} + +QComboBox:hover { +font-family: "微软雅黑"; +font-size: 13px; +padding: 3px 0x 3px 5px; +border-image: url(:/uiresource/box-01.png); +} + +QComboBox:pressed { +font-family: "微软雅黑"; +font-size: 13px; +padding: 3px 0x 3px 5px; +border-image: url(:/uiresource/box-01.png); +} + +QComboBox::drop-down { +subcontrol-origin: padding; +subcontrol-position: top right; width: 30 px; +border: 0px; +} + +QComboBox::down-arrow::!on { +image: url(:/uiresource/dropdow-01.png); +} +QComboBox::down-arrow::hover { +image: url(:/uiresource/dropdown-02.png); +} +QComboBox::down-arrow::on { +image: url(:/uiresource/dropdown-03.png); +} + +QListView { +font-family: "微软雅黑"; +font-size: 13px; +outline: 0px; +background-image: url(:/uiresource/list.png); +border-image: url(:/uiresource/list.png); +image: url(:/uiresource/list.png); +} + +QListView::item { +padding: 3px 0x 3px 5px; +border-width: 0px; +} + +QListView::item:selected { +background-color: rgb(74, 144, 226); +} + + + + + + + + + + + border-top: 1px solid rgb(234, 234, 234); + + + QFrame::Plain + + + Qt::Horizontal + + + + + + + + + QLabel{ +font-family: "Arial"; +font-size: 12px; +color:rgb(144,144,144); +}; + + + Audio Device + + + + + + + QComboBox { +font-family: "微软雅黑"; +font-size: 13px; +padding: 3px 0x 3px 5px; +border-image: url(:/uiresource/box-01.png); +} + +QComboBox:hover { +font-family: "微软雅黑"; +font-size: 13px; +padding: 3px 0x 3px 5px; +border-image: url(:/uiresource/box-01.png); +} + +QComboBox:pressed { +font-family: "微软雅黑"; +font-size: 13px; +padding: 3px 0x 3px 5px; +border-image: url(:/uiresource/box-01.png); +} + +QComboBox::drop-down { +subcontrol-origin: padding; +subcontrol-position: top right; width: 30 px; +border: 0px; +} + +QComboBox::down-arrow::!on { +image: url(:/uiresource/dropdow-01.png); +} +QComboBox::down-arrow::hover { +image: url(:/uiresource/dropdown-02.png); +} +QComboBox::down-arrow::on { +image: url(:/uiresource/dropdown-03.png); +} + +QListView { +font-family: "微软雅黑"; +font-size: 13px; +outline: 0px; +background-image: url(:/uiresource/list.png); +border-image: url(:/uiresource/list.png); +image: url(:/uiresource/list.png); +} + +QListView::item { +padding: 3px 0x 3px 5px; +border-width: 0px; +} + +QListView::item:selected { +background-color: rgb(74, 144, 226); +} + + + + + + + + + + + + 0 + 1 + + + + + 16777215 + 1 + + + + border-top: 1px solid rgb(234, 234, 234); + + + QFrame::Plain + + + Qt::Horizontal + + + + + + + + + QLabel{ +font-family: "Arial"; +font-size: 12px; +color:rgb(144,144,144); +}; + + + Video Device + + + + + + + QComboBox { +font-family: "微软雅黑"; +font-size: 13px; +padding: 3px 0x 3px 5px; +border-image: url(:/uiresource/box-01.png); +} + +QComboBox:hover { +font-family: "微软雅黑"; +font-size: 13px; +padding: 3px 0x 3px 5px; +border-image: url(:/uiresource/box-01.png); +} + +QComboBox:pressed { +font-family: "微软雅黑"; +font-size: 13px; +padding: 3px 0x 3px 5px; +border-image: url(:/uiresource/box-01.png); +} + +QComboBox::drop-down { +subcontrol-origin: padding; +subcontrol-position: top right; width: 30 px; +border: 0px; +} + +QComboBox::down-arrow::!on { +image: url(:/uiresource/dropdow-01.png); +} +QComboBox::down-arrow::hover { +image: url(:/uiresource/dropdown-02.png); +} +QComboBox::down-arrow::on { +image: url(:/uiresource/dropdown-03.png); +} + +QListView { +font-family: "微软雅黑"; +font-size: 13px; +outline: 0px; +background-image: url(:/uiresource/list.png); +border-image: url(:/uiresource/list.png); +image: url(:/uiresource/list.png); +} + +QListView::item { +padding: 3px 0x 3px 5px; +border-width: 0px; +} + +QListView::item:selected { +background-color: rgb(74, 144, 226); +} + + + + + + + + + + + + 0 + 1 + + + + + 16777215 + 1 + + + + border-top: 1px solid rgb(234, 234, 234); + + + QFrame::Plain + + + Qt::Horizontal + + + + + + + + + QLabel{ +font-family: "Arial"; +font-size: 12px; +color:rgb(144,144,144); +}; + + + Speaker + + + + + + + QComboBox { +font-family: "微软雅黑"; +font-size: 13px; +padding: 3px 0x 3px 5px; +border-image: url(:/uiresource/box-01.png); +} + +QComboBox:hover { +font-family: "微软雅黑"; +font-size: 13px; +padding: 3px 0x 3px 5px; +border-image: url(:/uiresource/box-01.png); +} + +QComboBox:pressed { +font-family: "微软雅黑"; +font-size: 13px; +padding: 3px 0x 3px 5px; +border-image: url(:/uiresource/box-01.png); +} + +QComboBox::drop-down { +subcontrol-origin: padding; +subcontrol-position: top right; width: 30 px; +border: 0px; +} + +QComboBox::down-arrow::!on { +image: url(:/uiresource/dropdow-01.png); +} +QComboBox::down-arrow::hover { +image: url(:/uiresource/dropdown-02.png); +} +QComboBox::down-arrow::on { +image: url(:/uiresource/dropdown-03.png); +} + +QListView { +font-family: "微软雅黑"; +font-size: 13px; +outline: 0px; +background-image: url(:/uiresource/list.png); +border-image: url(:/uiresource/list.png); +image: url(:/uiresource/list.png); +} + +QListView::item { +padding: 3px 0x 3px 5px; +border-width: 0px; +} + +QListView::item:selected { +background-color: rgb(74, 144, 226); +} + + + + + + + + + + + + 0 + 1 + + + + + 16777215 + 1 + + + + border-top: 1px solid rgb(234, 234, 234); + + + QFrame::Plain + + + Qt::Horizontal + + + + + + + + + QLabel{ +font-family: "Arial"; +font-size: 14px; + +}; + + + Audio + + + + + + + QPushButton:!pressed { +width:50px; +height:30px; +border-radius:19px; +image: url(:/uiresource/switch-open.png); +} + + + + + + + + + + Qt::Horizontal + + + + 20 + 20 + + + + + + + + QLabel{ +font-family: "Arial"; +font-size: 14px; +}; + + + Video + + + + + + + QPushButton:!pressed { +width:50px; +height:30px; +border-radius:19px; +image: url(:/uiresource/switch-open.png); +} + + + + + + + + + + + + + 0 + 1 + + + + + 16777215 + 1 + + + + border-top: 1px solid rgb(234, 234, 234); + + + QFrame::Plain + + + Qt::Horizontal + + + + + + + + + QLabel{ +font-family: "Arial"; +font-size: 12px; +color:rgb(144,144,144); +}; + + + Log Filter + + + + + + + QComboBox { +font-family: "微软雅黑"; +font-size: 13px; +padding: 3px 0x 3px 5px; +border-image: url(:/uiresource/box-01.png); +} + +QComboBox:hover { +font-family: "微软雅黑"; +font-size: 13px; +padding: 3px 0x 3px 5px; +border-image: url(:/uiresource/box-01.png); +} + +QComboBox:pressed { +font-family: "微软雅黑"; +font-size: 13px; +padding: 3px 0x 3px 5px; +border-image: url(:/uiresource/box-01.png); +} + +QComboBox::drop-down { +subcontrol-origin: padding; +subcontrol-position: top right; width: 30 px; +border: 0px; +} + +QComboBox::down-arrow::!on { +image: url(:/uiresource/dropdow-01.png); +} +QComboBox::down-arrow::hover { +image: url(:/uiresource/dropdown-02.png); +} +QComboBox::down-arrow::on { +image: url(:/uiresource/dropdown-03.png); +} + +QListView { +font-family: "微软雅黑"; +font-size: 13px; +outline: 0px; +background-image: url(:/uiresource/list.png); +border-image: url(:/uiresource/list.png); +image: url(:/uiresource/list.png); +} + +QListView::item { +padding: 3px 0x 3px 5px; +border-width: 0px; +} + +QListView::item:selected { +background-color: rgb(74, 144, 226); +} + + + + + + + + + + + + 0 + 1 + + + + + 16777215 + 1 + + + + border-top: 1px solid rgb(234, 234, 234); + + + QFrame::Plain + + + Qt::Horizontal + + + + + + + + + QLabel{ +font-family: "Arial"; +font-size: 12px; +color:rgb(144,144,144); +}; + + + Beauty Effect + + + + + + + Qt::Horizontal + + + + 20 + 20 + + + + + + + + + 50 + 30 + + + + + 50 + 30 + + + + QPushButton:!hover { +border-image: url(:/uiresource/switch-off.png); +background-image: url(:/uiresource/switch-off.png); +} + +QPushButton:hover { +border-image: url(:/uiresource/switch-off.png); +background-image: url(:/uiresource/switch-off.png); +} + + + + + + false + + + + + + + + + + + QLabel{ +font-family: "Arial"; +font-size: 12px; +color:rgb(144,144,144); +}; + + + Contrast Level + + + + + + + Qt::Horizontal + + + + 20 + 20 + + + + + + + + + 194 + 32 + + + + + 194 + 32 + + + + QComboBox { +font-family: "微软雅黑"; +font-size: 13px; +padding: 3px 0x 3px 5px; +border-image: url(:/uiresource/box-01.png); +} + +QComboBox:hover { +font-family: "微软雅黑"; +font-size: 13px; +padding: 3px 0x 3px 5px; +border-image: url(:/uiresource/box-01.png); +} + +QComboBox:pressed { +font-family: "微软雅黑"; +font-size: 13px; +padding: 3px 0x 3px 5px; +border-image: url(:/uiresource/box-01.png); +} + +QComboBox::drop-down { +subcontrol-origin: padding; +subcontrol-position: top right; width: 30 px; +border: 0px; +} + +QComboBox::down-arrow::!on { +image: url(:/uiresource/dropdow-01.png); +} +QComboBox::down-arrow::hover { +image: url(:/uiresource/dropdown-02.png); +} +QComboBox::down-arrow::on { +image: url(:/uiresource/dropdown-03.png); +} + +QListView { +font-family: "微软雅黑"; +font-size: 13px; +outline: 0px; +background-image: url(:/uiresource/list.png); +border-image: url(:/uiresource/list.png); +image: url(:/uiresource/list.png); +} + +QListView::item { +padding: 3px 0x 3px 5px; +border-width: 0px; +} + +QListView::item:selected { +background-color: rgb(74, 144, 226); +} + + + + + + + + + + + + + QLabel{ +font-family: "Arial"; +font-size: 12px; +color:rgb(144,144,144); +}; + + + Lightening(0.00) + + + + + + + QSlider::groove:horizontal { + border:1px; + border-color: rgba(240,240,240,255); + border-radius:3px; + height: 6px; + margin: 0px 0; + left: 4px; right: 4px; + background: rgba(240,240,240,255); + } +QSlider::handle:horizontal { + + background-image: url(:/uiresource/slider.png); + background-repeat: none; background-position: center; + width: 20px; + height: 20px; + margin: -9px 0; +} +QSlider::sub-page:horizontal{ + border:1px; + border-color: #44A2FC; + border-radius:3px; + background: #44A2FC; +}; + + + 100 + + + 1 + + + 10 + + + Qt::Horizontal + + + + + + + + + + + QLabel{ +font-family: "Arial"; +font-size: 12px; +color:rgb(144,144,144); +}; + + + Smoothness(0.00) + + + + + + + QSlider::groove:horizontal { + border:1px; + border-color: rgba(240,240,240,255); + border-radius:3px; + height: 6px; + margin: 0px 0; + left: 4px; right: 4px; + background: rgba(240,240,240,255); + } +QSlider::handle:horizontal { + + background-image: url(:/uiresource/slider.png); + background-repeat: none; background-position: center; + width: 20px; + height: 20px; + margin: -9px 0; +} +QSlider::sub-page:horizontal{ + border:1px; + border-color: #44A2FC; + border-radius:3px; + background: #44A2FC; +}; + + + 100 + + + 1 + + + 10 + + + Qt::Horizontal + + + + + + + + + + + QLabel{ +font-family: "Arial"; +font-size: 12px; +color:rgb(144,144,144); +}; + + + Redness(0.00) + + + + + + + QSlider::groove:horizontal { + border:1px; + border-color: rgba(240,240,240,255); + border-radius:3px; + height: 6px; + margin: 0px 0; + left: 4px; right: 4px; + background: rgba(240,240,240,255); + } +QSlider::handle:horizontal { + + background-image: url(:/uiresource/slider.png); + background-repeat: none; background-position: center; + width: 20px; + height: 20px; + margin: -9px 0; +} +QSlider::sub-page:horizontal{ + border:1px; + border-color: #44A2FC; + border-radius:3px; + background: #44A2FC; +}; + + + 100 + + + 1 + + + 10 + + + Qt::Horizontal + + + + + + + + + + 0 + 1 + + + + + 16777215 + 1 + + + + border-top: 1px solid rgb(234, 234, 234); + + + QFrame::Plain + + + Qt::Horizontal + + + + + + + + + + + diff --git a/Group-Video/OpenVideoCall-Windows/build_release.bat b/Group-Video/OpenVideoCall-Windows/build_release.bat new file mode 100644 index 00000000..e97bf581 --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/build_release.bat @@ -0,0 +1,24 @@ +@echo off + +title qmake and nmake build prompt +::C:\Program Files (x86)\Microsoft Visual Studio 12.0\VC +::C:\Program Files (x86)\Microsoft Visual Studio\2017\Community\VC\Auxiliary\Build; +set VCINSTALLDIR=%~1 +::C:\Qt\5.12.2\msvc2017;C:\Qt\5.12.2\msvc2017_64 +set QTDIR=%~2 +::x86;x64 +set Machine=%~3 +echo vsdir: %VCINSTALLDIR% +echo qtdir:%QTDIR% +echo machine:%Machine% + +set PATH=%VCINSTALLDIR%\bin;%QTDIR%\bin;C:\Program Files\7-Zip;%PATH% + +::shadow build +set vsdevpath=%VCINSTALLDIR%\vcvarsall.bat +echo vsdevpath:%vsdevpath% +call "%VCINSTALLDIR%\vcvarsall.bat" %Machine% +qmake OpenVideoCall.pro "CONFIG+=release" "CONFIG+=qml_release" +nmake +cd release +windeployqt OpenVideoCall.exe \ No newline at end of file diff --git a/Group-Video/OpenVideoCall-Windows/enterroom.cpp b/Group-Video/OpenVideoCall-Windows/enterroom.cpp new file mode 100644 index 00000000..b2f6791c --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/enterroom.cpp @@ -0,0 +1,195 @@ +#include "enterroom.h" +#include "ui_enterroom.h" +#include "agoraobject.h" +#include "qgraphicseffect.h" +#include "agorawindowmanager.h" + + EnterRoom::EnterRoom(QWidget *parent) : + QMainWindow(parent), + ui(new Ui::wgEnterRoom) +{ + ui->setupUi(this); + + this->setWindowFlags(Qt::FramelessWindowHint | Qt::WindowSystemMenuHint | Qt::WindowStaysOnTopHint); + this->setAttribute(Qt::WA_TranslucentBackground); + this->setAttribute(Qt::WA_TransparentForMouseEvents); + + AgoraWindowManager::getInstance()->insertItem(qWndType_EnterRoom,this); +} + +EnterRoom::~EnterRoom() +{ + delete ui; +} + +void EnterRoom::mousePressEvent(QMouseEvent *e) +{ + if(e->button() == Qt::LeftButton) { + m_mousePosition = e->pos(); + if(m_mousePosition.x() < lnTitleWidth && + m_mousePosition.y() < lnTitleHeight) + m_bMousePressed = true; + } +} + +void EnterRoom::mouseMoveEvent(QMouseEvent *e) +{ + if(m_bMousePressed == true) { + QPoint movePos = e->globalPos() - m_mousePosition; + move(movePos); + e->accept(); + } +} + +void EnterRoom::mouseReleaseEvent(QMouseEvent *e) +{ + m_bMousePressed = false; +} + +void EnterRoom::focusInEvent(QFocusEvent *event) +{ + this->show(); +} + +void EnterRoom::focusOutEvent(QFocusEvent *event) +{ + this->hide(); +} + +void EnterRoom::joinchannel(const QString& qsChannel,uint uid) +{ + ui->lbChannel->setText(qsChannel); + this->show(); +} + +void EnterRoom::leavechannel() +{ +} + +void EnterRoom::setChannelName(const QString& qsChannelInfo) +{ + ui->lbChannel->setText(qsChannelInfo); +} + +void EnterRoom::setParam(const QString& qsParam) +{ + ui->lbParam->setText(qsParam); +} + +int EnterRoom::getR1() +{ + return m_uidr1; +} + +int EnterRoom::getR2() +{ + return m_uidr2; +} + +int EnterRoom::getR3() +{ + return m_uidr3; +} + +void EnterRoom::switchUidText(const QString &qsSrc,const QString &qsDest,int nIndex) +{ + QString qsInfo1; + qsInfo1.sprintf("%s,%s,%d",qsSrc.toStdString().c_str(),qsDest.toStdString().c_str(),nIndex); + //qDebug(qsInfo1.toStdString().c_str()); + ui->lbChannel->setText(qsSrc); + if(1 == nIndex) + ui->lb_r1->setText(qsDest); + if(2 == nIndex) + ui->lb_r2->setText(qsDest); + if(3 == nIndex) + ui->lb_r3->setText(qsDest); +} + +void EnterRoom::on_rbCamera_stateChanged(int arg1) +{ + if(arg1 == Qt::Unchecked) + CAgoraObject::getInstance()->MuteLocalVideo(FALSE); + else if(arg1 == Qt::Checked) + CAgoraObject::getInstance()->MuteLocalVideo(TRUE); +} + +void EnterRoom::on_rbMic_stateChanged(int arg1) +{ + if(arg1 == Qt::Unchecked) + CAgoraObject::getInstance()->MuteLocalAudio(FALSE); + else if(arg1 == Qt::Checked) + CAgoraObject::getInstance()->MuteLocalAudio(TRUE); +} + +void EnterRoom::setAllRAtt(int nRCount) +{ + ui->lb_r1->setVisible(false); + ui->lb_r2->setVisible(false); + ui->lb_r3->setVisible(false); + ui->lb_count->setVisible(false); + + if(nRCount >= 1) { + QString qsText; + qsText.sprintf(" uid:%u",m_uidr1); + ui->lb_r1->setText(qsText); + ui->lb_r1->setVisible(true); + + QRect qrt = ui->lb_count->geometry(); + QRect qrt1 = ui->lb_r1->geometry(); + qrt.setTop(qrt1.bottom() + 10); + ui->lb_count->move(qrt.left(),qrt.top()); + ui->lb_count->setVisible(true); + + } + if(nRCount >= 2) { + QString qsText; + qsText.sprintf(" uid:%u",m_uidr2); + ui->lb_r2->setText(qsText); + ui->lb_r2->setVisible(true); + + QRect qrt = ui->lb_count->geometry(); + QRect qrt1 = ui->lb_r2->geometry(); + qrt.setTop(qrt1.bottom() + 10); + ui->lb_count->move(qrt.left(),qrt.top()); + ui->lb_count->setVisible(true); + } + if(nRCount >= 3) { + QString qsText; + qsText.sprintf(" uid:%u",m_uidr3); + ui->lb_r3->setText(qsText); + ui->lb_r3->setVisible(true); + + QRect qrt = ui->lb_count->geometry(); + QRect qrt1 = ui->lb_r3->geometry(); + qrt.setTop(qrt1.bottom() + 10); + ui->lb_count->move(qrt.left(),qrt.top()); + ui->lb_count->setVisible(true); + } + + QString qsCount; + qsCount.sprintf("Total %d Person",nRCount + 1); + ui->lb_count->setText(qsCount); +} + +void EnterRoom::setR1(uid_t uid) +{ + m_uidr1 = uid; +} + +void EnterRoom::setR2(uid_t uid) +{ + m_uidr2 = uid; +} + +void EnterRoom::setR3(uid_t uid) +{ + m_uidr3 = uid; +} + +void EnterRoom::on_btnLeave_clicked() +{ + QMainWindow *pLastWnd = AgoraWindowManager::getInstance()->getQWnd(qWndType_InRoom); + connect(this,SIGNAL(sender_exitChannel()),pLastWnd,SLOT(leavechannel())); + emit sender_exitChannel(); + this->hide(); +} diff --git a/Group-Video/OpenVideoCall-Windows/enterroom.h b/Group-Video/OpenVideoCall-Windows/enterroom.h new file mode 100644 index 00000000..0c6a8166 --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/enterroom.h @@ -0,0 +1,68 @@ +#ifndef ENTERROOM_H +#define ENTERROOM_H + +#include +#include +#include + +namespace Ui { +class wgEnterRoom; +} + +class EnterRoom : public QMainWindow +{ + Q_OBJECT + +public: + explicit EnterRoom(QWidget *parent = 0); + ~EnterRoom(); + + void joinchannel(const QString& qsChannel,uint uid); + void leavechannel(); + + void setChannelName(const QString& qsChannelInfo); + void setParam(const QString& qsParam); + + void setAllRAtt(int nRCount); + void setR1(unsigned int uid); + void setR2(unsigned int uid); + void setR3(unsigned int uid); + int getR1(); + int getR2(); + int getR3(); + + void switchUidText(const QString &qsSrc,const QString &qsDest,int nIndex); + +protected: + virtual void mousePressEvent(QMouseEvent *e); + virtual void mouseMoveEvent(QMouseEvent *e); + virtual void mouseReleaseEvent(QMouseEvent *e); + + virtual void focusInEvent(QFocusEvent *event); + virtual void focusOutEvent(QFocusEvent *event); + +signals: + void sender_exitChannel(); + void sender_updateVideo(); + +private slots: + + void on_rbCamera_stateChanged(int arg1); + void on_rbMic_stateChanged(int arg1); + void on_btnLeave_clicked(); + +private: + const int lnTitleWidth = 1366; + const int lnTitleHeight = 30; + QPoint m_mousePosition; + bool m_bMousePressed; + +private: + Ui::wgEnterRoom *ui; + QMainWindow* m_pLastWnd; + unsigned int m_uidr1; + unsigned int m_uidr2; + unsigned int m_uidr3; +}; + +#endif // ENTERROOM_H diff --git a/Group-Video/OpenVideoCall-Windows/enterroom.ui b/Group-Video/OpenVideoCall-Windows/enterroom.ui new file mode 100644 index 00000000..330e4412 --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/enterroom.ui @@ -0,0 +1,295 @@ + + + wgEnterRoom + + + + 0 + 0 + 1366 + 768 + + + + Form + + + QWidget { + width:1366px; + height:768px; +} + + + + + 618 + 20 + 200 + 32 + + + + + HelveticaNeue + -1 + + + + false + + + QLabel { + width:200px; + height:44px; + + font-size:16px; + font-family:HelveticaNeue; + color:rgba(255,255,255,1); + line-height:18px; +} + + + baluoteliz + + + Qt::AlignCenter + + + + + + 1024 + 37 + 264 + 32 + + + + false + + + QLabel { + width:264px; + height:32px; + + image: url(:/uiresource/Groupparam.png); + border-radius:4px; + opacity:0.4; + font-size:12px; + font-family:HelveticaNeue; + color:rgba(238,238,238,1); + line-height:18px; +} + + + SD-RTN: 10000ms. Video: 15fps 640x480 + + + Qt::AlignCenter + + + + + + 1296 + 558 + 50 + 50 + + + + false + + + QCheckBox::indicator{ + width:50px; + height:50px; +} + +QCheckBox:indicator:unchecked:!hover { + image: url(:/uiresource/icon-camera.png); +} +QCheckBox:indicator:unchecked:hover { + image: url(:/uiresource/icon-camera on.png); +} + +QCheckBox:indicator:checked:!hover { + image: url(:/uiresource/icon-camera off.png); +} +QCheckBox:indicator:checked:hover { + image: url(:/uiresource/icon-camera off.png); +} + + + RadioButton + + + true + + + false + + + + + + 1296 + 628 + 50 + 50 + + + + false + + + QCheckBox::indicator{ + width:50px; + height:50px; +} + +QCheckBox:indicator:unchecked:!hover { + image: url(:/uiresource/icon-micorophone.png); +} +QCheckBox:indicator:unchecked:hover { + image: url(:/uiresource/icon-micorophone on.png); +} + +QCheckBox:indicator:checked:!hover { + image: url(:/uiresource/icon-micorophone off.png); +} +QCheckBox:indicator:checked:hover { + image: url(:/uiresource/icon-micorophone off.png); +} + + + RadioButton + + + true + + + false + + + + + + 30 + 574 + 200 + 32 + + + + width:200px; +height:32px; +image: url(:/uiresource/count.png); +border-radius:4px; +opacity:0.4; +font-size:14px; +font-family:HelveticaNeue; +color:#ffffff; +line-height:16px; + + + Total 7 Person + + + Qt::AlignCenter + + + + + + 35 + 214 + 111 + 20 + + + + width:83px; +height:20px; +image: url(:/uiresource/remoteuid.png); +border-radius:10px; +font-size:12px; +font-family:HelveticaNeue; +color:#ffffff; +line-height:14px; + + + uid:r1 + + + + + + 40 + 534 + 111 + 20 + + + + width:83px; +height:20px; +image: url(:/uiresource/remoteuid.png); +border-radius:10px; +font-size:12px; +font-family:HelveticaNeue; +color:#ffffff; +line-height:14px; + + + uid:r3 + + + + + + 40 + 374 + 111 + 20 + + + + width:83px; +height:20px; +image: url(:/uiresource/remoteuid.png); +border-radius:10px; +font-size:12px; +font-family:HelveticaNeue; +color:#ffffff; +line-height:14px; + + + uid:r2 + + + + + + 1296 + 698 + 50 + 50 + + + + QPushButton:!hover{ + border-image: url(:/uiresource/icon-hang up hover.png); +} +QPushButton:hover{ + border-image: url(:/uiresource/icon-hang up.png); +} + + + + + + + + + diff --git a/Group-Video/OpenVideoCall-Windows/inroom.cpp b/Group-Video/OpenVideoCall-Windows/inroom.cpp new file mode 100644 index 00000000..5af4ac17 --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/inroom.cpp @@ -0,0 +1,388 @@ +#include "agoraobject.h" +#include "inroom.h" +#include "ui_inroom.h" +#include "agorawindowmanager.h" + +#ifdef Q_OS_WIN32 +#include +#endif + +InRoom::InRoom(QWidget *parent) : + QMainWindow(parent), + ui(new Ui::InRoom) +{ + ui->setupUi(this); + this->setWindowFlags(Qt::FramelessWindowHint | Qt::WindowSystemMenuHint + | Qt::WindowMinMaxButtonsHint ); + + CAgoraObject* pObject = CAgoraObject::getInstance(); + AgoraWindowManager::getInstance()->insertItem(qWndType_InRoom,this); + + connect(pObject,SIGNAL(sender_videoStopped()), + this,SLOT(receive_videoStopped())); + connect(pObject,SIGNAL(sender_joinedChannelSuccess(const QString&,unsigned int ,int)), + this,SLOT(receive_joinedChannelSuccess(const QString&,unsigned int,int))); + connect(pObject,SIGNAL(sender_userJoined(unsigned int,int)), + this,SLOT(receive_userJoined(unsigned int,int))); + connect(pObject,SIGNAL(sender_userOffline(unsigned int,USER_OFFLINE_REASON_TYPE)), + this,SLOT(receive_userOffline(unsigned int,USER_OFFLINE_REASON_TYPE))); + connect(pObject,SIGNAL(sender_firstLocalVideoFrame(int,int,int)), + this,SLOT(receive_firstLocalVideoFrame(int,int,int))); + connect(pObject,SIGNAL(sender_firstRemoteVideoDecoded(unsigned int,int,int,int)), + this,SLOT(receive_firstRemoteVideoDecoded(unsigned int,int,int,int))); + connect(pObject,SIGNAL(sender_firstRemoteVideoFrameDrawn(unsigned int,int,int,int)), + this,SLOT(receive_firstRemoteVideoFrameDrawn(unsigned int,int,int,int))); + connect(pObject,SIGNAL(sender_localVideoStats(LocalVideoStats)), + this,SLOT(receive_localVideoStats(LocalVideoStats))); + connect(pObject,SIGNAL(sender_remoteVideoStats(RemoteVideoStats)), + this,SLOT(receive_remoteVideoStats(RemoteVideoStats))); + connect(pObject,SIGNAL(sender_rtcStats(RtcStats)), + this,SLOT(receive_rtcStats(RtcStats))); + + ui->widget_l->lower(); + ui->widget_r1->raise(); + ui->widget_r2->raise(); + ui->widget_r3->raise(); + ui->widget_r1->setWindowOpacity(1);//opaque. + ui->widget_r2->setWindowOpacity(1); + ui->widget_r3->setWindowOpacity(1); + + ui->widget_l->installEventFilter(this); + ui->widget_r1->installEventFilter(this); + ui->widget_r2->installEventFilter(this); + ui->widget_r3->installEventFilter(this); + + m_timer_fps = new QTimer(this); + connect(m_timer_fps,SIGNAL(timeout()),this,SLOT(receive_timer_pfs())); +} + +InRoom::~InRoom() +{ + delete ui; +} + +void InRoom::mousePressEvent(QMouseEvent *e) +{ + if(e->button() == Qt::LeftButton) { + m_mousePosition = e->pos(); + if(m_mousePosition.x() < lnTitleWidth && + m_mousePosition.y() < lnTitleHeight) + m_bMousePressed = true; + } + + QApplication::sendEvent(m_uper.get(),e); +} + +void InRoom::mouseMoveEvent(QMouseEvent *e) +{ + if(m_bMousePressed == true) { + QPoint movePos = e->globalPos() - m_mousePosition; + move(movePos); + e->accept(); + } + + + QApplication::sendEvent(m_uper.get(),e); +} + +void InRoom::mouseReleaseEvent(QMouseEvent *e) +{ + m_bMousePressed = false; + + QApplication::sendEvent(m_uper.get(),e); +} + +void InRoom::focusInEvent(QFocusEvent *event) +{ + QApplication::sendEvent(m_uper.get(),event); +} + +void InRoom::focusOutEvent(QFocusEvent *event) +{ + QApplication::sendEvent(m_uper.get(),event); +} + +void InRoom::joinchannel(const QString& qsChannelId,const QString& qsChannelKey,uint uid) +{ + this->show(); + + CAgoraObject::getInstance()->joinChannel((qsChannelKey.length() > 0 ? qsChannelKey:NULL),qsChannelId,uid); + + m_uper.reset(new EnterRoom); + m_uper->joinchannel(qsChannelId,uid); +} + +void InRoom::leavechannel() +{ + m_timer_fps->stop(); + { + std::lock_guard autoLock(m_vsMutex); + m_qivs.clear(); + delete m_timer_fps; + m_bigUid = 0; + m_uid = 0; + } + + CAgoraObject::getInstance()->leaveChannel(); + this->hide(); + + QMainWindow* pLastWnd = AgoraWindowManager::getInstance()->getQWnd(qWndType_OpenVideoCall); + pLastWnd->show(); +} + +void InRoom::receive_videoStopped() +{ +} + +void InRoom::receive_joinedChannelSuccess(const QString &qsChannel, unsigned int uid, int elapsed) +{ + { + std::lock_guard autoLock(m_vsMutex); + m_uid = uid; + if(!m_qivs.contains(uid)) { + m_qivs[uid] = Video_Stats(uid); + } + } + + adjustPos(); + + QString qsChannelInfo; + m_qsChannel = qsChannel; + qsChannelInfo.sprintf("%s %u",qsChannel.toStdString().c_str(),uid); + m_uper->setChannelName(qsChannelInfo); + m_bigUid = uid; + m_timer_fps->start(2000); +} + +void InRoom::receive_userJoined(uid_t uid, int elapsed) +{ + { + std::lock_guard autoLock(m_vsMutex); + if(!m_qivs.contains(uid)) { + m_qivs[uid] = Video_Stats(uid); + } + } + + adjustPos(); +} + +void InRoom::receive_userOffline(uid_t uid, USER_OFFLINE_REASON_TYPE reason) +{ + { + std::lock_guard autoLock(m_vsMutex); + if(m_qivs.contains(uid)) { + auto it = m_qivs.find(uid); + m_qivs.erase(it); + } + } + + adjustPos(); +} + +void InRoom::receive_firstLocalVideoFrame(int width, int height, int elapsed) +{ + +} + +void InRoom::receive_firstRemoteVideoDecoded(uid_t uid, int width, int height, int elapsed) +{ + +} + +void InRoom::receive_firstRemoteVideoFrameDrawn(uid_t uid, int width, int height, int elapsed) +{ + +} + +void InRoom::receive_localVideoStats(const LocalVideoStats &stats) +{ + { + std::lock_guard autoLock(m_vsMutex); + if(m_qivs.contains(m_uid)) { + m_qivs[m_uid].nWidth = stats.encodedFrameWidth; + m_qivs[m_uid].nHeight = stats.encodedFrameHeight; + m_qivs[m_uid].nFps = stats.sentFrameRate; + m_qivs[m_uid].nBitrate = stats.sentBitrate; + } + } +} + +void InRoom::receive_remoteVideoStats(const RemoteVideoStats &stats) +{ + { + std::lock_guard autoLock(m_vsMutex); + if(m_qivs.contains(stats.uid)) { + m_qivs[stats.uid].nLastmileDelay = stats.delay; + m_qivs[stats.uid].nWidth = stats.width; + m_qivs[stats.uid].nHeight = stats.height; + m_qivs[stats.uid].nFps = stats.rendererOutputFrameRate; + m_qivs[stats.uid].nBitrate = stats.receivedBitrate; + } + } +} + +void InRoom::receive_rtcStats(const RtcStats &stats) +{ + m_nlastmileDelay = stats.lastmileDelay; + + std::lock_guard autoLock(m_vsMutex); + if(m_qivs.contains(m_uid)) + m_qivs[m_uid].nLastmileDelay = stats.lastmileDelay; +} + +void InRoom::receive_timer_pfs() +{ + std::lock_guard autoLock(m_vsMutex); + if(m_qivs.contains(m_bigUid)) { + QString qsFps; + auto it = m_qivs.value(m_bigUid); + qsFps.sprintf("SD-RTN: %dms. Video: %dfps %dx%d",it.nLastmileDelay,it.nFps,it.nWidth,it.nHeight); + m_uper->setParam(qsFps); + } +} + +void InRoom::adjustPos() +{ + ui->widget_l->setVisible(false); + ui->widget_r1->setVisible(false); + ui->widget_r2->setVisible(false); + ui->widget_r3->setVisible(false); + + std::lock_guard autoLock(m_vsMutex); + auto it = m_qivs.begin(); + int nIndex = 0; + while(m_qivs.end() != it) { + if(it->uid == m_uid) { + m_bigUid == m_uid; + it->pWidget = ui->widget_l; + it->nIndex = 0; + CAgoraObject::getInstance()->LocalVideoPreview((HWND)(it->pWidget->winId()), + TRUE, + (it->uid == m_bigUid) ? RENDER_MODE_FIT : RENDER_MODE_HIDDEN); + ui->widget_l->setVisible(true); + ui->widget_l->setGeometry(0,0,1366,768); + ui->widget_l->lower(); + QString qsChannelInfo; + qsChannelInfo.sprintf("%s %u",m_qsChannel.toStdString().c_str(),m_uid); + m_uper->setChannelName(qsChannelInfo); + } + else { + nIndex++; + if(nIndex == 1) { + it->pWidget = ui->widget_r1; + it->nIndex = 1; + CAgoraObject::getInstance()->RemoteVideoRender(it->uid, + (HWND)(it->pWidget->winId()), + (it->uid == m_bigUid) ? RENDER_MODE_FIT:RENDER_MODE_HIDDEN); + m_uper->setR1(it->uid); + ui->widget_r1->setVisible(true); + ui->widget_r1->setGeometry(30,94,200,150); + ui->widget_r1->raise(); + } + + if(nIndex == 2) { + it->pWidget = ui->widget_r2; + it->nIndex = 2; + CAgoraObject::getInstance()->RemoteVideoRender(it->uid, + (HWND)(it->pWidget->winId()), + (it->uid == m_bigUid) ? RENDER_MODE_FIT:RENDER_MODE_HIDDEN); + m_uper->setR2(it->uid); + ui->widget_r2->setVisible(true); + ui->widget_r2->setGeometry(30,254,200,150); + ui->widget_r2->raise(); + } + + if(nIndex == 3) { + it->pWidget = ui->widget_r3; + it->nIndex = 3; + CAgoraObject::getInstance()->RemoteVideoRender(it->uid, + (HWND)(it->pWidget->winId()), + (it->uid == m_bigUid) ? RENDER_MODE_FIT:RENDER_MODE_HIDDEN); + m_uper->setR3(it->uid); + ui->widget_r3->setVisible(true); + ui->widget_r3->setGeometry(30,414,200,150); + ui->widget_r3->raise(); + } + } + it++; + } + + m_uper->setAllRAtt(nIndex); +} + +bool InRoom::eventFilter(QObject *watched,QEvent *event) +{ + bool bFind = false; + int nIndex = 0; + Video_Stats vsr,vsbig; + if(watched==ui->widget_r1 && event->type() == QEvent::MouseButtonDblClick) { + qDebug("DBClick r1"); + std::lock_guard autoLock(m_vsMutex); + uid_t uid = m_uper->getR1(); + if(m_qivs.contains(uid) && m_qivs.contains(m_bigUid)) { + vsr = m_qivs[uid]; + vsbig = m_qivs[m_bigUid]; + bFind = ( vsr.uid == m_bigUid ) ? false : true; + nIndex = vsr.nIndex; + } + } + else if(watched == ui->widget_r2 && event->type() == QEvent::MouseButtonDblClick) { + qDebug("DBClick r2"); + std::lock_guard autoLock(m_vsMutex); + uid_t uid = m_uper->getR2(); + if(m_qivs.contains(uid) && m_qivs.contains(m_bigUid)) { + vsr = m_qivs[uid]; + vsbig = m_qivs[m_bigUid]; + bFind = (vsr.uid == m_bigUid) ? false : true; + nIndex = vsr.nIndex; + } + } + else if(watched == ui->widget_r3 && event->type() == QEvent::MouseButtonDblClick) { + qDebug("DBClick r3"); + std::lock_guard autoLock(m_vsMutex); + uid_t uid = m_uper->getR3(); + if(m_qivs.contains(uid) && m_qivs.contains(m_bigUid)) { + vsr = m_qivs[uid]; + vsbig = m_qivs[m_bigUid]; + bFind = (vsr.uid == m_bigUid) ? false : true; + nIndex = vsr.nIndex; + } + } + + else if(watched == ui->widget_l && event->type() == QEvent::MouseButtonDblClick) { + qDebug("DBClick local"); + std::lock_guard autoLock(m_vsMutex); + uid_t uid = m_uid; + if(m_qivs.contains(uid) && m_qivs.contains(m_bigUid)) { + vsr = m_qivs[uid]; + vsbig = m_qivs[m_bigUid]; + bFind = (vsr.uid == m_bigUid) ? false : true; + nIndex = vsr.nIndex; + } + } + + if(bFind) { + std::lock_guard autolock(m_vsMutex); + QRect qrr,qrbig; + if(vsr.pWidget) + qrr = vsr.pWidget->geometry(); + if(vsbig.pWidget) + qrbig = vsbig.pWidget->geometry(); + + vsr.pWidget->setGeometry(qrbig); + vsbig.pWidget->setGeometry(qrr); + vsr.pWidget->lower(); + vsbig.pWidget->raise(); + m_qivs[vsr.uid].nIndex = 0; + m_qivs[vsbig.uid].nIndex = nIndex; + + QString qsSrc,qsDest; + qsSrc.sprintf("%s %u",m_qsChannel.toStdString().c_str(),vsr.uid); + qsDest.sprintf(" uid:%u",vsbig.uid); + m_uper->switchUidText(qsSrc,qsDest,nIndex); + + m_bigUid = vsr.uid; + } + + return QWidget::eventFilter(watched,event); +} diff --git a/Group-Video/OpenVideoCall-Windows/inroom.h b/Group-Video/OpenVideoCall-Windows/inroom.h new file mode 100644 index 00000000..96b0eca5 --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/inroom.h @@ -0,0 +1,109 @@ +#ifndef INROOM_H +#define INROOM_H + +#include +#include +#include +#include "enterroom.h" +#include +#include + +#include +using namespace agora::rtc; + +namespace Ui { +class InRoom; +} + +typedef struct eTagVideoStats { + eTagVideoStats(){;} + eTagVideoStats(unsigned int ui,int nlastmiledelay = 0,int nwidth = 0,int nheight = 0,int nfps = 0,int nbitrate = 0,QWidget *pwidget = Q_NULLPTR,int nindex = 0): + uid(ui),nLastmileDelay(nlastmiledelay),nWidth(nwidth),nHeight(nheight),nFps(nfps),nBitrate(nbitrate),pWidget(pwidget),nIndex(nindex){;} + eTagVideoStats(const eTagVideoStats& vss) { + *this = vss; + } + eTagVideoStats& operator=(const eTagVideoStats& vss) { + if(this != &vss) { + uid = vss.uid; + nLastmileDelay = vss.nLastmileDelay; + nWidth = vss.nWidth; + nHeight = vss.nHeight; + nFps = vss.nFps; + nBitrate = vss.nBitrate; + pWidget = vss.pWidget; + nIndex = vss.nIndex; + } + + return *this; + } + + unsigned int uid; + int nLastmileDelay; + int nWidth; + int nHeight; + int nFps; + int nBitrate; + QWidget* pWidget; + int nIndex; +}Video_Stats,*PVideo_Stats,*LPVideoStats; +typedef QMap qIVS; + +class InRoom : public QMainWindow +{ + Q_OBJECT + +public: + explicit InRoom(QWidget *parent = 0); + ~InRoom(); + +private: + Ui::InRoom *ui; + +protected: + virtual void mousePressEvent(QMouseEvent *e); + virtual void mouseMoveEvent(QMouseEvent *e); + virtual void mouseReleaseEvent(QMouseEvent *e); + + virtual void focusInEvent(QFocusEvent *event); + virtual void focusOutEvent(QFocusEvent *event); + +public slots: + void joinchannel(const QString& qsChannelId,const QString& qsChannelKey,uint uid); + void leavechannel(); + + void receive_videoStopped(); + void receive_joinedChannelSuccess(const QString &qsChannel, unsigned int uid, int elapsed); + void receive_userJoined(unsigned int uid, int elapsed); + void receive_userOffline(unsigned int uid, USER_OFFLINE_REASON_TYPE reason); + void receive_firstLocalVideoFrame(int width, int height, int elapsed); + void receive_firstRemoteVideoDecoded(unsigned int uid, int width, int height, int elapsed); + void receive_firstRemoteVideoFrameDrawn(unsigned int uid, int width, int height, int elapsed); + void receive_localVideoStats(const LocalVideoStats &stats); + void receive_remoteVideoStats(const RemoteVideoStats &stats); + void receive_rtcStats(const RtcStats &stats); + + void receive_timer_pfs(); + + bool eventFilter(QObject *watched,QEvent *event); + +private slots: + +private: + void adjustPos(); + +private: + const int lnTitleWidth = 1366; + const int lnTitleHeight = 30; + QPoint m_mousePosition; + bool m_bMousePressed; + std::unique_ptr m_uper; + std::mutex m_vsMutex; + qIVS m_qivs; + int m_nlastmileDelay; + QTimer *m_timer_fps; + uid_t m_uid; + uid_t m_bigUid; + QString m_qsChannel; +}; + +#endif // INROOM_H diff --git a/Group-Video/OpenVideoCall-Windows/inroom.ui b/Group-Video/OpenVideoCall-Windows/inroom.ui new file mode 100644 index 00000000..0eec14da --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/inroom.ui @@ -0,0 +1,98 @@ + + + InRoom + + + + 0 + 0 + 1366 + 768 + + + + MainWindow + + + + background-color:#999999; + + + + + 30 + 94 + 200 + 150 + + + + image: url(:/uiresource/allmute remote.png); +border-color: #D8D8D8; +border-size:1px; +border-radius:2px; + + + + + + 30 + 254 + 200 + 150 + + + + image: url(:/uiresource/allmute remote.png); +border-color: #D8D8D8; +border-size:1px; +border-radius:2px; + + + + + + 30 + 414 + 200 + 150 + + + + image: url(:/uiresource/allmute remote.png); +border-color: #D8D8D8; +border-size:1px; +border-radius:2px; + + + + + + 0 + 0 + 1366 + 768 + + + + + + 543 + 228 + 280 + 280 + + + + image: url(:/uiresource/allmute.png); + + + + + + + + + + + diff --git a/Group-Video/OpenVideoCall-Windows/inroomdig.cpp b/Group-Video/OpenVideoCall-Windows/inroomdig.cpp new file mode 100644 index 00000000..ef81d699 --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/inroomdig.cpp @@ -0,0 +1,61 @@ +#include "inroomdig.h" +#include "ui_inroomdig.h" +#include "agoraobject.h" +#include "qquickwidget.h" +#include "QHBoxLayout" +#include "QStackedLayout" + +InRoomDig::InRoomDig(QWidget *parent) : + QDialog(parent), + ui(new Ui::InRoomDig) +{ + ui->setupUi(this); + this->setWindowFlags(Qt::FramelessWindowHint | Qt::Dialog); + //this->setAttribute(Qt::WA_TranslucentBackground); + initWindow(); +} + +InRoomDig::~InRoomDig() +{ + delete ui; +} + +void InRoomDig::initWindow() +{ + QString strDir = QCoreApplication::applicationDirPath(); + strDir.append("\\AgoraSDK.log"); + CAgoraObject::getInstance(this)->setLogPath(strDir); + + CAgoraObject::getInstance()->enableAudio(true); + CAgoraObject::getInstance()->enableVideo(true); + CAgoraObject::getInstance()->EnableWebSdkInteroperability(true); + CAgoraObject::getInstance()->SetChannelProfile(CHANNEL_PROFILE_COMMUNICATION); + CAgoraObject::getInstance()->joinChannel("","233",0); + + QHBoxLayout *main_layout = new QHBoxLayout(); + QStackedLayout *stacked_layout = new QStackedLayout(); + stacked_layout->setMargin(0); + stacked_layout->setStackingMode(QStackedLayout::StackAll); + + QLabel* player_status_ = new QLabel("test", this); + player_status_->setGeometry(618,20,130,32); + player_status_->move(618,20); + player_status_->resize(130,32); + QPalette pe; + pe.setColor(QPalette::WindowText, Qt::red); + player_status_->setPalette(pe); + player_status_->setAlignment(Qt::AlignCenter|Qt::AlignCenter); + + stacked_layout->addWidget(player_status_); + main_layout->addLayout(stacked_layout); + setLayout(main_layout); + player_status_->raise(); + + QWidget* player_video_ = new QWidget(); + player_video_->setGeometry(0,0,1366,768); + player_video_->setLayout(main_layout); + // this->setCentralWidget(player_video_); + player_video_->show(); + + CAgoraObject::getInstance()->LocalVideoPreview((HWND)(player_video_->winId()),TRUE); +} diff --git a/Group-Video/OpenVideoCall-Windows/inroomdig.h b/Group-Video/OpenVideoCall-Windows/inroomdig.h new file mode 100644 index 00000000..e54ab5c0 --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/inroomdig.h @@ -0,0 +1,26 @@ +#ifndef INROOMDIG_H +#define INROOMDIG_H + +#include +#include + +namespace Ui { +class InRoomDig; +} + +class InRoomDig : public QDialog +{ + Q_OBJECT + +public: + explicit InRoomDig(QWidget *parent = 0); + ~InRoomDig(); + + void initWindow(); + +private: + Ui::InRoomDig *ui; + QLabel* m_labText; +}; + +#endif // INROOMDIG_H diff --git a/Group-Video/OpenVideoCall-Windows/inroomdig.ui b/Group-Video/OpenVideoCall-Windows/inroomdig.ui new file mode 100644 index 00000000..6c56e0b7 --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/inroomdig.ui @@ -0,0 +1,22 @@ + + + InRoomDig + + + + 0 + 0 + 1366 + 768 + + + + Dialog + + + + + + + + diff --git a/Group-Video/OpenVideoCall-Windows/main.cpp b/Group-Video/OpenVideoCall-Windows/main.cpp new file mode 100644 index 00000000..59af23a2 --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/main.cpp @@ -0,0 +1,32 @@ +#include "openvideocall.h" +#include "avdevice.h" +#include "nettesting.h" +#include "nettestresult.h" +#include "inroom.h" +#include "enterroom.h" +#include +#include +using namespace agora::rtc; + +Q_DECLARE_METATYPE(USER_OFFLINE_REASON_TYPE) +Q_DECLARE_METATYPE(LocalVideoStats) +Q_DECLARE_METATYPE(RemoteVideoStats) +Q_DECLARE_METATYPE(RtcStats) +Q_DECLARE_METATYPE(LastmileProbeResult) + +int main(int argc, char *argv[]) +{ + QApplication a(argc, argv); + a.setWindowIcon(QIcon("openvideocall.ico")); + + qRegisterMetaType(); + qRegisterMetaType(); + qRegisterMetaType(); + qRegisterMetaType(); + qRegisterMetaType(); + + OpenVideoCall w; + w.show(); + + return a.exec(); +} diff --git a/Group-Video/OpenVideoCall-Windows/nettestdetail.cpp b/Group-Video/OpenVideoCall-Windows/nettestdetail.cpp new file mode 100644 index 00000000..aff698e4 --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/nettestdetail.cpp @@ -0,0 +1,80 @@ +#include "nettestdetail.h" +#include "ui_nettestdetail.h" +#include "agorawindowmanager.h" +#include + +NetTestDetail::NetTestDetail(QWidget *parent) : + QMainWindow(parent), + ui(new Ui::NetTestDetail) +{ + ui->setupUi(this); + this->setWindowFlags(Qt::FramelessWindowHint | Qt::WindowSystemMenuHint); + this->setAttribute(Qt::WA_TranslucentBackground); + + AgoraWindowManager::getInstance()->insertItem(qWndType_NetTestDetail,this); +} + +NetTestDetail::~NetTestDetail() +{ + delete ui; +} + +void NetTestDetail::receiver_network_detail(int quality,const LastmileProbeResult& lr) +{ + qDebug(__FUNCTION__); + + ui->lb_rtt_up->setText(QString::number(lr.rtt)); + ui->lb_lost_up->setText(QString::number(lr.uplinkReport.packetLossRate)); + ui->lb_lost_down->setText(QString::number(lr.downlinkReport.packetLossRate)); + ui->lb_bandwidth_up->setText(QString::number(lr.uplinkReport.availableBandwidth)); + ui->lb_bandwidth_down->setText(QString::number(lr.downlinkReport.availableBandwidth)); +} + +void NetTestDetail::mousePressEvent(QMouseEvent *e) +{ + if(e->button() == Qt::LeftButton) { + m_mousePosition = e->pos(); + if(m_mousePosition.x() < lnTitleWidth && + m_mousePosition.x() >= lnGapWidth && + m_mousePosition.y() >= lnGapHeight && + m_mousePosition.y() < lnTitleHeight) + m_bMousePressed = true; + } +} + +void NetTestDetail::mouseMoveEvent(QMouseEvent *e) +{ + if(m_bMousePressed == true) { + QPoint movePos = e->globalPos() - m_mousePosition; + move(movePos); + e->accept(); + } +} + +void NetTestDetail::mouseReleaseEvent(QMouseEvent *e) +{ + m_bMousePressed = false; +} + +void NetTestDetail::on_btn_back_clicked() +{ + this->hide(); + QMainWindow* pWnd = AgoraWindowManager::getInstance()->getQWnd(qWndType_OpenVideoCall); + if(pWnd) + pWnd->show(); +} + +void NetTestDetail::on_btn_min_clicked() +{ + this->showMinimized(); +} + +void NetTestDetail::on_btn_close_clicked() +{ + on_btn_back_clicked(); +} + +void NetTestDetail::on_btn_ok_clicked() +{ + on_btn_back_clicked(); +} diff --git a/Group-Video/OpenVideoCall-Windows/nettestdetail.h b/Group-Video/OpenVideoCall-Windows/nettestdetail.h new file mode 100644 index 00000000..805ba88a --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/nettestdetail.h @@ -0,0 +1,51 @@ +#ifndef NETTESTDETAIL_H +#define NETTESTDETAIL_H + +#include +#include +#include +using namespace agora::rtc; + +namespace Ui { +class NetTestDetail; +} + +class NetTestDetail : public QMainWindow +{ + Q_OBJECT + +public: + explicit NetTestDetail(QWidget *parent = 0); + ~NetTestDetail(); + +protected slots: + void receiver_network_detail(int quality,const LastmileProbeResult& lr); + +protected: + virtual void mousePressEvent(QMouseEvent *e); + virtual void mouseMoveEvent(QMouseEvent *e); + virtual void mouseReleaseEvent(QMouseEvent *e); + +private slots: + void on_btn_back_clicked(); + + void on_btn_min_clicked(); + + void on_btn_close_clicked(); + + void on_btn_ok_clicked(); + +private: + const int lnGapWidth = 18; + const int lnGapHeight = 12; + const int lnTitleWidth = 718; + const int lnTitleHeight = 30; + QPoint m_mousePosition; + bool m_bMousePressed; + + +private: + Ui::NetTestDetail *ui; +}; + +#endif // NETTESTDETAIL_H diff --git a/Group-Video/OpenVideoCall-Windows/nettestdetail.ui b/Group-Video/OpenVideoCall-Windows/nettestdetail.ui new file mode 100644 index 00000000..1591de06 --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/nettestdetail.ui @@ -0,0 +1,283 @@ + + + NetTestDetail + + + + 0 + 0 + 786 + 536 + + + + MainWindow + + + + image: url(:/uiresource/OVC-win-netdetail.png); + + + + + 418 + 25 + 36 + 36 + + + + QPushButton:!hover{ +border-image: url(:/uiresource/icon-back.png); +image: url(:/uiresource/icon-back.png); +} + +QPushButton:hover:!pressed{ +border-image: url(:/uiresource/icon-back hover.png); +image: url(:/uiresource/icon-back hover.png); +} + +QPushButton:!hover:pressed{ +border-image: url(:/uiresource/icon-back.png); +image: url(:/uiresource/icon-back.png); +} + + + + + + + + + 698 + 34 + 18 + 18 + + + + QPushButton:!hover{ + border-image: url(:/uiresource/icon-min default.png); + image: url(:/uiresource/icon-min default.png); +} + +QPushButton:hover:!pressed{ + border-image: url(:/uiresource/icon-min hover.png); + image: url(:/uiresource/icon-min hover.png); +} + +QPushButton:!hover:pressed{ + border-image: url(:/uiresource/icon-min default.png); + image: url(:/uiresource/icon-min default.png); +} + + + + + + + + + 726 + 34 + 18 + 18 + + + + QPushButton:!hover{ + border-image: url(:/uiresource/icon-close default.png); + image: url(:/uiresource/icon-close default.png); +} + +QPushButton:hover:!pressed{ + border-image: url(:/uiresource/icon-close hover.png); + image: url(:/uiresource/icon-close hover.png); +} + +QPushButton:!hover:pressed{ + border-image: url(:/uiresource/icon-close default.png); + image: url(:/uiresource/icon-close default.png); +} + + + + + + + + + 528 + 87 + 64 + 20 + + + + font-size:14px; +font-family:PingFangSC-Regular,PingFangSC; +font-weight:400; +color:rgba(102,102,102,1); +line-height:20px; +image: url(:/uiresource/edit1.png); + + + TextLabel + + + + + + 676 + 87 + 63 + 20 + + + + font-size:14px; +font-family:PingFangSC-Regular,PingFangSC; +font-weight:400; +color:rgba(102,102,102,1); +line-height:20px; +image: url(:/uiresource/edit1.png); + + + + + + + + + 676 + 133 + 63 + 20 + + + + font-size:14px; +font-family:PingFangSC-Regular,PingFangSC; +font-weight:400; +color:rgba(102,102,102,1); +line-height:20px; +image: url(:/uiresource/edit1.png); + + + TextLabel + + + + + + 528 + 133 + 64 + 20 + + + + font-size:14px; +font-family:PingFangSC-Regular,PingFangSC; +font-weight:400; +color:rgba(102,102,102,1); +line-height:20px; +image: url(:/uiresource/edit1.png); + + + TextLabel + + + + + + 528 + 179 + 119 + 20 + + + + font-size:14px; +font-family:PingFangSC-Regular,PingFangSC; +font-weight:400; +color:rgba(102,102,102,1); +line-height:20px; +border-image: url(:/uiresource/edit4.png); +image: url(:/uiresource/edit4.png); + + + TextLabel + + + + + + 676 + 179 + 63 + 20 + + + + font-size:14px; +font-family:PingFangSC-Regular,PingFangSC; +font-weight:400; +color:rgba(102,102,102,1); +line-height:20px; +image: url(:/uiresource/edit1.png); + + + TextLabel + + + + + + 418 + 437 + 325 + 44 + + + + QPushButton:!hover { +font-size:17px; +font-family:HelveticaNeue; +color:rgba(0,106,216,1); +line-height:20px; +background:rgba(255,255,255,1); +border-radius:2px; +border:1px solid rgba(204,204,204,1); +image: url(:/uiresource/edit1.png); +} +QPushButton:hover:pressed { +font-size:17px; +font-family:HelveticaNeue; +color:rgba(0,106,216,1); +line-height:20px; +background:rgba(255,255,255,1); +border-radius:2px; +border:1px solid rgba(204,204,204,1); +image: url(:/uiresource/edit1.png); +} +QPushButton:hover:!pressed { +font-size:17px; +font-family:HelveticaNeue; +color:rgba(255,255,255,1); +line-height:20px; +background:rgba(0,106,216,1); +border-radius:2px; +border:1px solid rgba(204,204,204,1); +image: url(:/uiresource/edit2.png); +} + + + OK + + + + + + + diff --git a/Group-Video/OpenVideoCall-Windows/nettesting.cpp b/Group-Video/OpenVideoCall-Windows/nettesting.cpp new file mode 100644 index 00000000..b8e60ef2 --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/nettesting.cpp @@ -0,0 +1,96 @@ +#include "nettesting.h" +#include "ui_nettesting.h" +#include +#include "agoraobject.h" +#include "agorawindowmanager.h" + +NetTesting::NetTesting(QWidget *parent) : + QMainWindow(parent), + ui(new Ui::NetTesting) +{ + ui->setupUi(this); + + this->setWindowFlags(Qt::FramelessWindowHint | Qt::WindowSystemMenuHint); + this->setAttribute(Qt::WA_TranslucentBackground); + + CAgoraObject* pInstance = CAgoraObject::getInstance(); + connect(pInstance,SIGNAL(sender_lastmileQuality(int)),this,SLOT(receive_lastmileQuality(int))); + connect(pInstance,SIGNAL(sender_lastmileProbeResult(const LastmileProbeResult&)),this,SLOT(receive_lastmileProbeResult(LastmileProbeResult))); + + CAgoraObject::getInstance()->startLastMileProbeTest(true); + QMovie* pMovie = new QMovie("uiresource\\loading.gif"); + ui->lb_status->setMovie(pMovie); + pMovie->start(); + + AgoraWindowManager::getInstance()->insertItem(qWndType_NetTesting,this); +} + +NetTesting::~NetTesting() +{ + delete ui; +} + +void NetTesting::on_btn_back_clicked() +{ + this->hide(); + CAgoraObject::getInstance()->startLastMileProbeTest(false); + QMainWindow* pWnd = AgoraWindowManager::getInstance()->getQWnd(qWndType_OpenVideoCall); + if(pWnd) + pWnd->show(); +} + +void NetTesting::on_btn_min_clicked() +{ + this->showMinimized(); +} + +void NetTesting::on_btn_close_clicked() +{ + on_btn_back_clicked(); +} + +void NetTesting::receive_lastmileQuality(int quality) +{ + m_nQuality = quality; +} + +void NetTesting::receive_lastmileProbeResult(const LastmileProbeResult &result) +{ + if(m_nQuality >=1 && m_nQuality <= 6) + CAgoraObject::getInstance()->startLastMileProbeTest(false); + this->hide(); + m_lp = result; + + m_upNtr.reset(new NetTestResult()); + connect(this,SIGNAL(sender_network_result(int,LastmileProbeResult)), + m_upNtr.get(),SLOT(receiver_network_result(int,LastmileProbeResult))); + emit sender_network_result(m_nQuality,m_lp); + m_upNtr->show(); +} + +void NetTesting::mousePressEvent(QMouseEvent *e) +{ + if(e->button() == Qt::LeftButton) { + m_mousePosition = e->pos(); + if(m_mousePosition.x() < lnTitleWidth && + m_mousePosition.x() >= lnGapWidth && + m_mousePosition.y() >= lnGapHeight && + m_mousePosition.y() < lnTitleHeight) + m_bMousePressed = true; + } +} + +void NetTesting::mouseMoveEvent(QMouseEvent *e) +{ + if(m_bMousePressed == true) { + QPoint movePos = e->globalPos() - m_mousePosition; + move(movePos); + e->accept(); + } +} + +void NetTesting::mouseReleaseEvent(QMouseEvent *e) +{ + m_bMousePressed = false; +} + diff --git a/Group-Video/OpenVideoCall-Windows/nettesting.h b/Group-Video/OpenVideoCall-Windows/nettesting.h new file mode 100644 index 00000000..966b187a --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/nettesting.h @@ -0,0 +1,55 @@ +#ifndef NETTESTING_H +#define NETTESTING_H + +#include +#include +#include "nettestresult.h" +#include +#include +using namespace agora::rtc; + +namespace Ui { +class NetTesting; +} + +class NetTesting : public QMainWindow +{ + Q_OBJECT + +public: + explicit NetTesting(QWidget *parent = 0); + ~NetTesting(); + +signals: + void sender_network_result(int quality,const LastmileProbeResult& lr); + +private slots: + void on_btn_back_clicked(); + void on_btn_min_clicked(); + void on_btn_close_clicked(); + + void receive_lastmileQuality(int quality); + void receive_lastmileProbeResult(const LastmileProbeResult &result); + +protected: + virtual void mousePressEvent(QMouseEvent *e); + virtual void mouseMoveEvent(QMouseEvent *e); + virtual void mouseReleaseEvent(QMouseEvent *e); + +private: + const int lnGapWidth = 18; + const int lnGapHeight = 12; + const int lnTitleWidth = 718; + const int lnTitleHeight = 30; + QPoint m_mousePosition; + bool m_bMousePressed; + + int m_nQuality; + LastmileProbeResult m_lp; + +private: + std::unique_ptr m_upNtr; + Ui::NetTesting *ui; +}; + +#endif // NETTESTING_H diff --git a/Group-Video/OpenVideoCall-Windows/nettesting.ui b/Group-Video/OpenVideoCall-Windows/nettesting.ui new file mode 100644 index 00000000..b1601b29 --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/nettesting.ui @@ -0,0 +1,126 @@ + + + NetTesting + + + + 0 + 0 + 786 + 536 + + + + MainWindow + + + + image: url(:/uiresource/OVC-win-nettest.png); + + + + + 418 + 25 + 36 + 36 + + + + QPushButton:!hover { +border-image: url(:/uiresource/icon-back.png); +image: url(:/uiresource/icon-back.png); +} +QPushButton:hover:!pressed { +border-image: url(:/uiresource/icon-back hover.png); +image: url(:/uiresource/icon-back hover.png); +} +QPushButton:hover:pressed { +border-image: url(:/uiresource/icon-back.png); +image: url(:/uiresource/icon-back.png); +} + + + + + + + + + + 698 + 34 + 18 + 18 + + + + QPushButton:!hover{ +border-image: url(:/uiresource/icon-min default.png); +image: url(:/uiresource/icon-min default.png); +} + +QPushButton:hover:!pressed { +border-image: url(:/uiresource/icon-min hover.png); +image: url(:/uiresource/icon-min hover.png); +} + +QPushButton:hover:pressed{ +border-image: url(:/uiresource/icon-min default.png); +image: url(:/uiresource/icon-min default.png); +} + + + + + + + + + 726 + 34 + 18 + 18 + + + + QPushButton:!hover{ +border-image: url(:/uiresource/icon-close default.png); +image: url(:/uiresource/icon-close default.png); +} + +QPushButton:hover:!pressed { +border-image: url(:/uiresource/icon-close hover.png); +image: url(:/uiresource/icon-close hover.png); +} + +QPushButton:hover:pressed{ +border-image: url(:/uiresource/icon-close default.png); +image: url(:/uiresource/icon-close default.png); +} + + + + + + + + + 540 + 190 + 83 + 83 + + + + image: url(:/uiresource/edit5.png); + + + + + + + + + + diff --git a/Group-Video/OpenVideoCall-Windows/nettestresult.cpp b/Group-Video/OpenVideoCall-Windows/nettestresult.cpp new file mode 100644 index 00000000..4626eac6 --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/nettestresult.cpp @@ -0,0 +1,113 @@ +#include "nettestresult.h" +#include "ui_nettestresult.h" +#include "agorawindowmanager.h" + +NetTestResult::NetTestResult(QWidget *parent) : + QMainWindow(parent), + ui(new Ui::NetTestResult) +{ + ui->setupUi(this); + + this->setWindowFlags(Qt::FramelessWindowHint | Qt::WindowSystemMenuHint); + this->setAttribute(Qt::WA_TranslucentBackground); + + AgoraWindowManager::getInstance()->insertItem(qWndType_NetTestResult,this); +} + +NetTestResult::~NetTestResult() +{ + delete ui; +} + +void NetTestResult::receiver_network_result(int quality,const LastmileProbeResult& lr) +{ + m_nQuality = quality; + m_lr = lr; + QUALITY_TYPE qt = static_cast(quality); + qDebug("%s(%d)",__FUNCTION__,quality); + switch(qt) { + case QUALITY_TYPE::QUALITY_EXCELLENT: + case QUALITY_TYPE::QUALITY_GOOD: { + ui->lb_status->setStyleSheet("QLabel{image: url(:/uiresource/pic-good.png)}"); + ui->lb_status_desc->setText("Your NetWork is Great"); + } + break; + case QUALITY_TYPE::QUALITY_POOR:{ + ui->lb_status->setStyleSheet("QLabel{image: url(:/uiresource/pic-poor.png)}"); + ui->lb_status_desc->setText("Your NetWork is Poor"); + + } + break; + case QUALITY_TYPE::QUALITY_BAD: + case QUALITY_TYPE::QUALITY_VBAD: + case QUALITY_TYPE::QUALITY_DOWN:{ + ui->lb_status->setStyleSheet("QLabel{image: url(:/uiresource/pic-bad.png)}"); + ui->lb_status_desc->setText("Your NetWork is Bad"); + } + break; + default: { + ui->lb_status->setStyleSheet(""); + ui->lb_status_desc->setText("Your NetWork is Unknown"); + } + break; + }; +} + +void NetTestResult::mousePressEvent(QMouseEvent *e) +{ + if(e->button() == Qt::LeftButton) { + m_mousePosition = e->pos(); + if(m_mousePosition.x() < lnTitleWidth && + m_mousePosition.x() >= lnGapWidth && + m_mousePosition.y() >= lnGapHeight && + m_mousePosition.y() < lnTitleHeight) + m_bMousePressed = true; + } +} + +void NetTestResult::mouseMoveEvent(QMouseEvent *e) +{ + if(m_bMousePressed == true) { + QPoint movePos = e->globalPos() - m_mousePosition; + move(movePos); + e->accept(); + } +} + +void NetTestResult::mouseReleaseEvent(QMouseEvent *e) +{ + m_bMousePressed = false; +} + +void NetTestResult::on_btn_detail_clicked() +{ + this->hide(); + m_upntd.reset(new NetTestDetail()); + connect(this,SIGNAL(sender_network_detail(int,LastmileProbeResult)), + m_upntd.get(),SLOT(receiver_network_detail(int,LastmileProbeResult))); + emit sender_network_detail(m_nQuality,m_lr); + m_upntd->show(); +} + +void NetTestResult::on_btn_ok_clicked() +{ + on_btn_back_clicked(); +} + +void NetTestResult::on_btn_min_clicked() +{ + this->showMinimized(); +} + +void NetTestResult::on_btn_close_clicked() +{ + on_btn_back_clicked(); +} + +void NetTestResult::on_btn_back_clicked() +{ + this->hide(); + QMainWindow* pWnd = AgoraWindowManager::getInstance()->getQWnd(qWndType_OpenVideoCall); + if(pWnd) + pWnd->show(); +} diff --git a/Group-Video/OpenVideoCall-Windows/nettestresult.h b/Group-Video/OpenVideoCall-Windows/nettestresult.h new file mode 100644 index 00000000..fd8c0439 --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/nettestresult.h @@ -0,0 +1,61 @@ +#ifndef NETTESTRESULT_H +#define NETTESTRESULT_H + +#include +#include +#include "nettestdetail.h" +#include +#include +using namespace agora::rtc; + +namespace Ui { +class NetTestResult; +} + +class NetTestResult : public QMainWindow +{ + Q_OBJECT + +public: + explicit NetTestResult(QWidget *parent = 0); + ~NetTestResult(); + +signals: + void sender_network_detail(int quality,const LastmileProbeResult& lr); + +protected slots: + void receiver_network_result(int quality,const LastmileProbeResult& lr); + +protected: + virtual void mousePressEvent(QMouseEvent *e); + virtual void mouseMoveEvent(QMouseEvent *e); + virtual void mouseReleaseEvent(QMouseEvent *e); + +private slots: + void on_btn_detail_clicked(); + + void on_btn_ok_clicked(); + + void on_btn_min_clicked(); + + void on_btn_close_clicked(); + + void on_btn_back_clicked(); + +private: + const int lnGapWidth = 18; + const int lnGapHeight = 12; + const int lnTitleWidth = 718; + const int lnTitleHeight = 30; + QPoint m_mousePosition; + bool m_bMousePressed; + +private: + int m_nQuality; + LastmileProbeResult m_lr; + QMainWindow* m_pLastWnd; + Ui::NetTestResult *ui; + std::unique_ptr m_upntd; +}; + +#endif // NETTESTRESULT_H diff --git a/Group-Video/OpenVideoCall-Windows/nettestresult.ui b/Group-Video/OpenVideoCall-Windows/nettestresult.ui new file mode 100644 index 00000000..c4dd7138 --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/nettestresult.ui @@ -0,0 +1,241 @@ + + + NetTestResult + + + + 0 + 0 + 786 + 536 + + + + MainWindow + + + + image: url(:/uiresource/OVC-win-netresult.png); + + + + + 418 + 25 + 36 + 36 + + + + QPushButton:!hover{ +border-image: url(:/uiresource/icon-back.png); +image: url(:/uiresource/icon-back.png); +} + +QPushButton:hover:!pressed{ +border-image: url(:/uiresource/icon-back hover.png); +image: url(:/uiresource/icon-back hover.png); +} + +QPushButton:!hover:pressed{ +border-image: url(:/uiresource/icon-back.png); +image: url(:/uiresource/icon-back.png); +} + + + + + + + + + 698 + 34 + 18 + 18 + + + + QPushButton:!hover{ + border-image: url(:/uiresource/icon-min default.png); + image: url(:/uiresource/icon-min default.png); +} + +QPushButton:hover:!pressed{ + border-image: url(:/uiresource/icon-min hover.png); + image: url(:/uiresource/icon-min hover.png); +} + +QPushButton:!hover:pressed{ + border-image: url(:/uiresource/icon-min default.png); + image: url(:/uiresource/icon-min default.png); +} + + + + + + + + + 726 + 34 + 18 + 18 + + + + QPushButton:!hover{ + border-image: url(:/uiresource/icon-close default.png); + image: url(:/uiresource/icon-close default.png); +} + +QPushButton:hover:!pressed{ + border-image: url(:/uiresource/icon-close hover.png); + image: url(:/uiresource/icon-close hover.png); +} + +QPushButton:!hover:pressed{ + border-image: url(:/uiresource/icon-close default.png); + image: url(:/uiresource/icon-close default.png); +} + + + + + + + + + 531 + 157 + 100 + 100 + + + + image: url(:/uiresource/pic-good.png); + + + + + + + + + 418 + 378 + 325 + 44 + + + + QPushButton:!hover { +font-size:17px; +font-family:HelveticaNeue; +color:rgba(0,106,216,1); +line-height:20px; +background:rgba(255,255,255,1); +border-radius:2px; +border:1px solid rgba(204,204,204,1); +image: url(:/uiresource/edit1.png); +} +QPushButton:hover:pressed { +font-size:17px; +font-family:HelveticaNeue; +color:rgba(0,106,216,1); +line-height:20px; +background:rgba(255,255,255,1); +border-radius:2px; +border:1px solid rgba(204,204,204,1); +image: url(:/uiresource/edit1.png); +} +QPushButton:hover:!pressed { +font-size:17px; +font-family:HelveticaNeue; +color:rgba(255,255,255,1); +line-height:20px; +background:rgba(0,106,216,1); +border-radius:2px; +border:1px solid rgba(204,204,204,1); +image: url(:/uiresource/edit2.png); +} + + + Detail + + + + + + 418 + 437 + 325 + 44 + + + + QPushButton:!hover { +font-size:17px; +font-family:HelveticaNeue; +color:rgba(0,106,216,1); +line-height:20px; +background:rgba(255,255,255,1); +border-radius:2px; +border:1px solid rgba(204,204,204,1); +image: url(:/uiresource/edit1.png); +} +QPushButton:hover:pressed { +font-size:17px; +font-family:HelveticaNeue; +color:rgba(0,106,216,1); +line-height:20px; +background:rgba(255,255,255,1); +border-radius:2px; +border:1px solid rgba(204,204,204,1); +image: url(:/uiresource/edit1.png); +} +QPushButton:hover:!pressed { +font-size:17px; +font-family:HelveticaNeue; +color:rgba(255,255,255,1); +line-height:20px; +background:rgba(0,106,216,1); +border-radius:2px; +border:1px solid rgba(204,204,204,1); +image: url(:/uiresource/edit2.png); +} + + + OK + + + + + + 490 + 280 + 181 + 21 + + + + border-image: url(:/uiresource/edit1.png); +image: url(:/uiresource/edit1.png); +font-size:17px; +font-family:HelveticaNeue; +color:rgba(51,51,51,1); +line-height:20px; + + + TextLabel + + + Qt::AlignCenter + + + + + + + diff --git a/Group-Video/OpenVideoCall-Windows/openvideocall.cpp b/Group-Video/OpenVideoCall-Windows/openvideocall.cpp new file mode 100644 index 00000000..02f1b385 --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/openvideocall.cpp @@ -0,0 +1,116 @@ +#include "openvideocall.h" +#include "ui_openvideocall.h" +#include "agorawindowmanager.h" +#include "agoraobject.h" + +OpenVideoCall::OpenVideoCall(QWidget *parent) : + QMainWindow(parent), + ui(new Ui::OpenVideoCall), + m_upAvDevice(Q_NULLPTR) +{ + ui->setupUi(this); + + this->setWindowFlags(Qt::FramelessWindowHint | Qt::WindowSystemMenuHint); + this->setAttribute(Qt::WA_TranslucentBackground); + + AgoraWindowManager::getInstance()->insertItem(qWndType_OpenVideoCall,this); + initWindow(); +} + +OpenVideoCall::~OpenVideoCall() +{ + delete ui; +} + +void OpenVideoCall::initWindow() +{ + QString strDir = QCoreApplication::applicationDirPath(); + strDir.append("\\AgoraSDK.log"); + CAgoraObject::getInstance(this)->setLogPath(strDir); + + CAgoraObject::getInstance()->enableAudio(true); + CAgoraObject::getInstance()->enableVideo(true); + CAgoraObject::getInstance()->EnableWebSdkInteroperability(true); + CAgoraObject::getInstance()->SetChannelProfile(CHANNEL_PROFILE_COMMUNICATION); + + ui->com_encryp->addItem("aes-128-xts"); + ui->com_encryp->addItem("aes-128-ecb"); + ui->com_encryp->addItem("aes-256-xts"); + ui->com_encryp->setCurrentIndex(0); +} + +void OpenVideoCall::mousePressEvent(QMouseEvent *e) +{ + if(e->button() == Qt::LeftButton) { + m_mousePosition = e->pos(); + if(m_mousePosition.x() < lnTitleWidth && + m_mousePosition.x() >= lnGapWidth && + m_mousePosition.y() >= lnGapHeight && + m_mousePosition.y() < lnTitleHeight) + m_bMousePressed = true; + } +} + +void OpenVideoCall::mouseMoveEvent(QMouseEvent *e) +{ + if(m_bMousePressed == true) { + QPoint movePos = e->globalPos() - m_mousePosition; + move(movePos); + e->accept(); + } +} + +void OpenVideoCall::mouseReleaseEvent(QMouseEvent *e) +{ + m_bMousePressed = false; +} + +void OpenVideoCall::on_btn_close_clicked() +{ + this->close(); +} + +void OpenVideoCall::on_btn_min_clicked() +{ + this->showMinimized(); +} + +void OpenVideoCall::on_btn_config_clicked() +{ + this->hide(); + QString qsChannel = ui->led_classid->text(); + m_upAvDevice.reset(new AVDevice(this,qsChannel)); + m_upAvDevice->show(); +} + +void OpenVideoCall::on_led_classid_returnPressed() +{ + //todo;ignore. +} + +void OpenVideoCall::on_btn_test_network_clicked() +{ + this->hide(); + m_upNetTesting.reset(new NetTesting()); + m_upNetTesting->show(); +} + +void OpenVideoCall::on_btn_join_clicked() +{ + //to do joinchannel. + QString qsClassId = ui->led_classid->text(); + this->hide(); + + QString qsEncrypSecret = ui->led_key->text(); + QString qsEncrypMode = ui->com_encryp->currentText(); + CAgoraObject::getInstance()->SetEncryptionMode(qsEncrypSecret.toUtf8().data(),qsEncrypMode.toUtf8().data()); + + m_upInRoom.reset(new InRoom()); + m_upInRoom->joinchannel(qsClassId,APP_TOKEN,0); +} + +void OpenVideoCall::on_com_encryp_currentIndexChanged(const QString &arg1) +{ + QString qsEncrypSecret = ui->led_key->text(); + CAgoraObject::getInstance()->SetEncryptionMode(qsEncrypSecret.toUtf8().data(),arg1.toUtf8().data()); +} diff --git a/Group-Video/OpenVideoCall-Windows/openvideocall.h b/Group-Video/OpenVideoCall-Windows/openvideocall.h new file mode 100644 index 00000000..7d02fbd7 --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/openvideocall.h @@ -0,0 +1,55 @@ +#ifndef OPENVIDEOCALL_H +#define OPENVIDEOCALL_H + +#include +#include +#include "avdevice.h" +#include "nettesting.h" +#include +#include "inroom.h" + +namespace Ui { +class OpenVideoCall; +} + +class OpenVideoCall : public QMainWindow +{ + Q_OBJECT + +public: + explicit OpenVideoCall(QWidget *parent = 0); + ~OpenVideoCall(); + +protected: + virtual void mousePressEvent(QMouseEvent *e); + virtual void mouseMoveEvent(QMouseEvent *e); + virtual void mouseReleaseEvent(QMouseEvent *e); + + void initWindow(); + +private slots: + void on_btn_close_clicked(); + void on_btn_min_clicked(); + void on_btn_config_clicked(); + void on_led_classid_returnPressed(); + void on_btn_test_network_clicked(); + void on_btn_join_clicked(); + + void on_com_encryp_currentIndexChanged(const QString &arg1); + +private: + const int lnGapWidth = 18; + const int lnGapHeight = 12; + const int lnTitleWidth = 718; + const int lnTitleHeight = 30; + QPoint m_mousePosition; + bool m_bMousePressed; + +private: + Ui::OpenVideoCall *ui; + std::unique_ptr m_upAvDevice; + std::unique_ptr m_upNetTesting; + std::unique_ptr m_upInRoom; +}; + +#endif // OPENVIDEOCALL_H diff --git a/Group-Video/OpenVideoCall-Windows/openvideocall.ico b/Group-Video/OpenVideoCall-Windows/openvideocall.ico new file mode 100644 index 0000000000000000000000000000000000000000..3a363714050822780693af3cd4d203057bdda019 GIT binary patch literal 4286 zcmeH~dr;KZ701tSSr!#x5k(Y47!2}Io`O6yYSIu*HI*1OibyikY8$5M#FR(^J`hlR z@D?dFEGj5cKt%AJkmy1}6I){+wn=STYK&H`y29@M_Qjrl@7i|Kq6wX*f3%asd_4Ew zbMN=u-?{hVKqTQOAb`Zb)Z{@lo`^yKhG-rT;|@dYYy01?0G}h`Zj$&6sRZ^OlI+_5 z-ghw**^Yn{8%wpq)naai}*J{!aK`nUbv7E!t#D6 zhL#=VGU{rB{=>}DfVwx3v$>w?%?&tjjgrrQH;B(HiQ%`F#&mZri=EQ7Y{tWuJI3E! zI)lK}H=m8UdNwtJZ6&{?<}Y{@|fz-bVz2K%Zql@t^X?@Tq4a_~hcqJExzC zO74Ckm~f9rf>gZA4e){-2OX3RKc{m+Je^(=<8?A6s{6#ZqWIzu{MfWtVrW{yD)2xP zZ{4IpehsC-o8?-G&%fx$9p4P+&PCyE$5SF*bhRVIy^H|Y9rv=8?!sF|8)JggxMQwo zS5KkNr^7Qk7KRUYJvWtgyYUX{Py-E>>nl;?LqoTqQWD8E*uxw23gCfCC+=Di$Zhk( z_{dXX>)Pgrk~kj_hqJj222t0SaYud#{|9kiKx;if?%L-AsQsyF(QOODZgngQ;cMGm z*$hq7kLj4DmR!uWL-UVP5gC7k{MA$d_-=`kk1Y=5<|jgIEy*EEo0CHb8iF|J+y-{A z)U<~@;r9WduSMMby>I&x*7!C*5&TI@axnjKqZ^xR5U)nOn%uz<6ZvJ-M&3ht(B!*C zN{^!OwE zN%m+qS0TO!`Kyq>YDjugI^p|;eg%CWaDTCakEi(Z{@GKw{?Wh<^|J#>-i7!s3NY@Z zUgHk>3osaV&^`D8a0}zraxtk|pPWosGYe~UhaL~$PdANV({ALiprhv9qyi5#xfJ@P zG#?m@rNr8_v0R%Fz;%fMZv%DXJU_A&k|b{$yTX`9bLFix=Ck!G z(!@+A%-^KJ+QSQc_)eh{qfUaI#$x>6jXV!Bxdi!3XcFdJ!guiRGe;u#B(90`lfm>T&L<~(Cnu|sLhncAezn>~e zLLEy0_ZLchGR2cCqkMT!w9jQQrvl$r740)bLcCwZ!9*YUBbCv<+%U(RuWeAW3@zw= zfU_Gf&hU%OScrSDouUnebOoNTW;x^h$8lNs1TK%5aJekpJH0%7g8SCc@zfgY=a4F! z?nRYR6P*#8RUYnr3UlpMG2VP}%}9nGL(2-S4C6K;!}c%Aj@(=E26vETD4;B0L7y+b zq~g7ao?H~_#YJIW#^O+~F0`|YLdPwGPXQUAu{g}@#xBgMj2g$iX`^@`Ut(ymVJmeY zx2MQI95d!)9|few{i?&=vcvP0bxLk~(v3@|d2(UUSO?pK#@c}O@BN*@p1dzf&AQLo({Cb+VKcEVN8(FsoVjzsD6Wfl`1(2p-^!G@Kl^@6%mMviFZLZY@EYFKFzYVz{;T1QiG3*W<mP{&l(p z41m$Uk7&P67Vs&?n!rM14viFRzbZ50okLTB96tKjC>dl7WYHE-pwFUAumoelh`S7| z|EjWnt@Hn00sg$%<}&v=G3Sy${^aww0~;_2och!{wMnh>7y*=OU6j)0pYRy1)=jF$ b9L#b$>sW)ebD^;rTF{iB?eh6-j`m*xAP$7x literal 0 HcmV?d00001 diff --git a/Group-Video/OpenVideoCall-Windows/openvideocall.qrc b/Group-Video/OpenVideoCall-Windows/openvideocall.qrc new file mode 100644 index 00000000..18ebd381 --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/openvideocall.qrc @@ -0,0 +1,50 @@ + + + uiresource/icon-back hover.png + uiresource/icon-back.png + uiresource/icon-camera off.png + uiresource/icon-camera.png + uiresource/icon-close hover.png + uiresource/icon-hang up hover.png + uiresource/icon-hang up.png + uiresource/icon-loading.png + uiresource/icon-micorophone off.png + uiresource/icon-micorophone.png + uiresource/icon-setting hover.png + uiresource/icon-setting.png + uiresource/OVC-win-03.jpg + uiresource/OVC-win-config.png + uiresource/OVC-win-home.png + uiresource/OVC-win-more users.jpg + uiresource/OVC-win-netdetail.png + uiresource/OVC-win-netresult.png + uiresource/OVC-win-nettest.png + uiresource/gray.png + uiresource/icon-close default.png + uiresource/icon-min default.png + uiresource/icon-min hover.png + uiresource/edit.png + uiresource/edit1.png + uiresource/edit2.png + uiresource/switch-off.png + uiresource/switch-open.png + uiresource/edit3.png + uiresource/loading.gif + uiresource/pic-bad.png + uiresource/pic-good.png + uiresource/pic-poor.png + uiresource/edit4.png + uiresource/edit5.png + uiresource/icon-camera on.png + uiresource/icon-micorophone on.png + uiresource/allmute remote.png + uiresource/allmute.png + uiresource/mutevideo remote.png + uiresource/mutevideo.png + uiresource/box-01.png + uiresource/dropdow-01.png + uiresource/dropdown-02.png + uiresource/dropdown-03.png + uiresource/slider.png + + diff --git a/Group-Video/OpenVideoCall-Windows/openvideocall.rc b/Group-Video/OpenVideoCall-Windows/openvideocall.rc new file mode 100644 index 00000000..6b34d015 --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/openvideocall.rc @@ -0,0 +1 @@ + IDI_ICON ICON DISCARDABLE "openvideocall.ico" diff --git a/Group-Video/OpenVideoCall-Windows/openvideocall.ui b/Group-Video/OpenVideoCall-Windows/openvideocall.ui new file mode 100644 index 00000000..15daaade --- /dev/null +++ b/Group-Video/OpenVideoCall-Windows/openvideocall.ui @@ -0,0 +1,252 @@ + + + OpenVideoCall + + + + 0 + 0 + 786 + 536 + + + + MainWindow + + + + image: url(:/uiresource/OVC-win-home.png); + + + + + 726 + 34 + 18 + 18 + + + + QPushButton:!hover { +image: url(:/uiresource/icon-close default.png); +border-image: url(:/uiresource/icon-close default.png); +} + +QPushButton:hover { +image: url(:/uiresource/icon-close hover.png); +border-image: url(:/uiresource/icon-close hover.png); +} + + + + + + + + + 418 + 25 + 36 + 36 + + + + QPushButton:!hover { +border-image: url(:/uiresource/icon-setting.png); +image: url(:/uiresource/icon-setting.png); +} + +QPushButton:hover { +border-image: url(:/uiresource/icon-setting hover.png); +image: url(:/uiresource/icon-setting hover.png); +} + + + + + + + + + 698 + 34 + 18 + 18 + + + + QPushButton:!hover { +image: url(:/uiresource/icon-min default.png); +border-image: url(:/uiresource/icon-min default.png); +} + +QPushButton:hover { +image: url(:/uiresource/icon-min hover.png); +border-image: url(:/uiresource/icon-min hover.png); +} + + + + + + + + + 418 + 152 + 325 + 40 + + + + width:325px; +height:40px; +border-radius:2px; +image: url(:/uiresource/edit1.png); +font-size:14px; +font-family:HelveticaNeue; +color:rgba(153,153,153,1); +line-height:16px; + + + + Input Name + + + + + + 418 + 216 + 205 + 40 + + + + width:205px; +height:40px; +border-radius:2px; +image: url(:/uiresource/edit1.png); +font-size:14px; +font-family:HelveticaNeue; +color:rgba(153,153,153,1); +line-height:16px; + + + + Encryption key + + + + + + 418 + 378 + 325 + 44 + + + + QPushButton:!hover { +font-size:17px; +font-family:HelveticaNeue; +color:rgba(0,106,216,1); +line-height:20px; +background:rgba(255,255,255,1); +border-radius:2px; +border:1px solid rgba(204,204,204,1); +image: url(:/uiresource/edit1.png); +} +QPushButton:hover:pressed { +font-size:17px; +font-family:HelveticaNeue; +color:rgba(0,106,216,1); +line-height:20px; +background:rgba(255,255,255,1); +border-radius:2px; +border:1px solid rgba(204,204,204,1); +image: url(:/uiresource/edit1.png); +} +QPushButton:hover:!pressed { +font-size:17px; +font-family:HelveticaNeue; +color:rgba(255,255,255,1); +line-height:20px; +background:rgba(0,106,216,1); +border-radius:2px; +border:1px solid rgba(204,204,204,1); +image: url(:/uiresource/edit2.png); +} + + + Test your Network + + + + + + 418 + 437 + 325 + 44 + + + + QPushButton:!hover { +font-size:17px; +font-family:HelveticaNeue; +color:rgba(0,106,216,1); +line-height:20px; +background:rgba(255,255,255,1); +border-radius:2px; +border:1px solid rgba(204,204,204,1); +image: url(:/uiresource/edit1.png); +} +QPushButton:hover:pressed { +font-size:17px; +font-family:HelveticaNeue; +color:rgba(0,106,216,1); +line-height:20px; +background:rgba(255,255,255,1); +border-radius:2px; +border:1px solid rgba(204,204,204,1); +image: url(:/uiresource/edit1.png); +} + +QPushButton:hover:!pressed { +font-size:17px; +font-family:HelveticaNeue; +color:rgba(255,255,255,1); +line-height:20px; +background:rgba(0,106,216,1); +border-radius:2px; +border:1px solid rgba(204,204,204,1); +image: url(:/uiresource/edit2.png); +} + + + joinChannel + + + + + + 634 + 216 + 110 + 44 + + + + font-size:17px; +font-family:HelveticaNeue; +color:rgba(0,106,216,1); +line-height:20px; + + + + + + + + diff --git a/Group-Video/OpenVideoCall-Windows/uiresource/OVC-win-03.jpg b/Group-Video/OpenVideoCall-Windows/uiresource/OVC-win-03.jpg new file mode 100644 index 0000000000000000000000000000000000000000..c5d2415aaf471f207de024f4392327cec28fe504 GIT binary patch literal 1152181 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 w&`4d z8MNE^zN}PA&ammv8|*$L+;PI)uf$|bK(ktx*VjhoPxJ(G9Bk?X+&h(j1>w9&toY4C zX?U7s6v?2FA`;bM^3pWo6M_X3tJ(}>dg=y=aUO3VJA_ZSEnE+)hTlB94<`t;2Dd1* zodstRlAdlo23(?)@r2+$sa2rzd>D@ zSq`!drOLW1Q!0AuafpfqG)P&5sanaK$gIh0=^4wTPVbGz6OJJ6a8CF6QOVy3=fjf` zqobkqCL5#GCmK)qjaAo3y84SNg)$_x!$F~0IBO@6sOKsnK?eiY+i~1zjsKmmn!Vx(eY2@!}J!NJLd+HO&P%F|Meqdffb@9 zJWq$-m~86SbHn$xk|xH%l7zdMEEu?;wQm}wYQ@60RYJoW#Y8Lmq0X2%QDQ93Ms8Y_ z&WD*DX=lE6m-g=J?UvC#T(;)hay%+mGcU^*9Gn#zpU@!{%o%8@&*9lcnfo8B%iFAo ze}{c#weZ&1a8QtKMQAX-U31y@&%-PZHb$ZTxkmM7%cc{PXgmo{ZmVm`*?cU)i6AT6 zrqoSoXCc5KK$puGsB3Qx4Xq4}5~J)-O|A6$@B6$|lu*j8E7mpq9^f2?QoG=OOy5`F zFB;?Jw7CMlX;Qa9ZR|YR`3=Ewq<>=tSuT>?OOc{;X}5T2UG5%p>k=JF47$H+WGa3k z&a~F-oVB#A2k&Hx_T~7=yKoEC$O&nn8eVqsKC}(q6X`HyuDga0T$TMW9XmEW?x)&{ zi(@T7S3GXSKnc2RC&*AbG=4;m*_U8TsH5=70K&k?Nf1d-hiq0vrw(HY3pOveX!j+E z)V)(Qa?d884y;$=V>GLcL^hg9T^tK+kc8kFeVVq`ai5bzn>!2~)+$f82~=TygVnu& zY%}von&*f_;XYVv(4#X?dLmg`H|gwYlLU|NWQvaU5~Ugkw7`iGkslu)l6WUx*y^wO zV@kV=?6)#D?_8u?<;+bu{WNCsI#j-gS7v3c#X;bkfyqnX8|}nKjqI&(Z{4b=PZwSr z{882))88B2@HuF0o8Nb?;Qo}fW^i8^=UEiKvs9R9DjPKG{GR=U7gVLC`-I=}8y_#z zvAJCRbnI(c8PmI>EI&ff8w5&~lB08Jx-~#2(QSkRFN+^bsUG-)N+*6zn&VCofFQTt z=&f*;&F|yHiCXtsL3|_e1PS_*m*C29`iN?+#%1)`qd*~6emj6Gq84yF8zNkH)n-cy zdXb0e9VQIMlXdBbO)4Vsr1_+4tK038yPTZw~L2dkG73$ z#jl-2d_2qhgg0V-~5dN6N`I42f;olFV z$Knt<(pNRqN>1hX3x9^e!kJrvT}2C`vO-1vs_P@g3@k4Ts@o~FQBNs_ z;7dVtxZM~%n@Um`T6bPMU>41frmy+$7eE?|{B?16ZNmSC<5$vf3K2Z3Acq;;mU&K> zJ!04M+xG0$f374Ty|rC0lI%7(Q3H`D*Ewi>N)z_SH547IqDLBzO-ULLxW6b6h7aL3 zupw70x6T%H$C?nLxXd5pP&xjN^?+nQ-nQlB9^Z=Uy8@`g$39I?EeH^{EtURW!Mj<6~Vkm1Bp^k&;rY^d= zlb??sUYY3}Dk?7cW618|BGv0s{jC$tdY}%03H7ne;)FZ1&m#tbV96w%-e=+JHG@s? zu+$>qPdP#?-N4#T`~5qe0w-v6uipd~z@fcLLHL>LNL+G&^=A?>t*o{0yr#&A`C?w) zQ17qGfJvrU4s7TQp16w^>?ML0_vqcWX^P|K(Vz<`g>&eg?Xk0}gKK%W>f__~G+R4I zUoSl~X!{6RDM$-YQ=V^K*F-ue&GqPXkE{reB$uICezQbsqnD6Bvg%^(Y{~4)m~v^0 zRoUyYn-&|FNbQ8O)49J#_TZ%4L3TQOWq=`oru9Dd+rqyOtnG%%MBBF6D-BFV6kyI5 z<*pcr^l5tI+wWXus7E@^S}h~&mdTVYCZbGVQkGTJXz?+c%QD|t3!YUUpD$|??;Ul2 z*0+0w3^g%zvyT!t1$9V7EtXY>ocD?lbVRbP=1nx&2yZ56y0m|mJ0yl&DHw0$xj#o_ zOqn(K)u%1Gq;?$Cr5Fd@w{6|3P_xv_x*gV;5=dNJd`x~O=XCMEVV&ILnos=c(kpif zXlO5MqHTEo*S-2gOZX(Ku7B``>ACu0f=Uy(>*(+`J^$(N!#=2#n=V}yJ7!nk zPQ@qHamHNwv+!wC^>4mh-Q?Wy+dJ3Da#R5;l$?R&?3M+1mNM(din?yOr>VW8$98zy zxdr71vy1iQAfQ2KG38grNQgU7=Hy+_m*6zaFc8veZ^ z$$u=rM8%rDyz;jPM4;K*n>BY=FMjEs3i%?GIHXD5w$;M(73mw-&}Q76^TeZNm|}v# z$Z&Us-zi4L=r;4;XBTFAHFR!0Fsxo;@Ac$q&D?JT8}&o7t=;&qIb~(SmVGqZ3v}hM zl+^Oju!-$gkK82QF!CwR=UiD{J%Tz@a!?ny-N{LzU*9rCTXO4NLO2n2#6Hmvi`cL_M|MyJ_k z@{_@dCge^p@ipgUe4z}bJ}fz7%`tZ8_+M2>9H+wX~WsK)I98K9899_(NM8w*Dor*A2godY}4eTkpHuY^1$}b`K`5Td5%i|(?TS!4#D`@ zI}C->BO_B;vJys1Q=I$6X&kWya;^K&8@}Ve=ViilUj3R0C`%u=%c6t(K{w3!V=6{i z`&r%&{CwZx>6RyQRO*C3HaHXI+LO-UV4#bG&c5&u+I zb_=?-`nJ2w%HQ4_{RERh=z|f3Wow!x>tZ^+F4^7=zi<7*DCvy&Xk2)H*FsNy&+feo@_KmlzC9(42Rojn` z_XXW&FmJz1kP$ls_1M`s%FN@TkM#%VW_d~7&9f>?{TXR(o{tL*8%DnG*J|CtYd$n%$(BVCW1R>BuRQEPUKO^!>c6M(8_b9YhRIry?C@rT< z@Xp!fAw~b8fgNMm6c!9i;y!o3PfXQ{X-3pYrNLJBnVJagNpO!J-E~&X>;H!a9-yCx zQxuX1I(2zXl{1=8L`-W=b%au&`b5;cvd|?HK$JT6{4tK=I}->v(KzKmO+nWJoxtmh z$4qmEFbet{a*qLGBPZGO^?DvK41r3iuM z^`SK=#6SSU`PD3QnnDUs;-ALH^)Gz3?U*<9&$t>94zI=@nYG&(nge2p%e(_$61* zPxPInAouCW(~?vwX97j}F{nMh!w_A{vl<#DfC!##yki-b{-pqKBx;K!Qw_Ui+N|wo zcI1~}@0K8jJ;B8ev=WMfZS*nB~l!lPAr(>oR>WdVB z8K>q&-f=NbLdudR$4BH#>e%v6wco`U@mzxm9c~T_$%9EIgTM=AGNf&Z)56J2$wB@N z5w4T{{D7D3^o5lRM?*G9Q}rYtuhF_-IROL;eNu!KY?+H&M`>gME4xBUlBBddvd1V@ z+qrAD1UO^tDY=R^=m?OW*R+egy#;O9Ts0k@O=yqlcey_8=Rp?cm_6C-;H2qzBx08fTuB7jH6zlsUm8 zl4hgY6ZRk4**3g?x!}o0Wo6Qd!CDM3qa2>-S>d12OFpY9XDZn5UCf^e6bOyTwR5+Q z!Ok~NC+2LFFomoXNz=I75)T$@@dy&fffup9AO`i>*$NQkZNK9Opss1V7|MPg&WT&x zI;QBvIE4Qnc0@dH&LI@55C1CFlpXzIJKw2ZnEaDFlFl^owUX0^U6w6)OBNXXkE+nV z&P`WN+2pzNc8+W0ks$#PAM=lVM%5vEyPuqLhIXhK13jVWK0^FKB&&*BclPG3Kg6S* zt}GAYbInF^lWs|XFP4BvI^tv+*~=L5R=zi>zNTVq0K%iX`ny=H8z8eUnon_qFKR6?TKImKSPseb!E z3FF`MytML&C9 ze!4E_Cnb?y(S(_;U-Ikumpyq~!Cho}x7q*3f}3emWGvhABzmu?;xgr*0GnpNC#Vvb zw7{PSMSjuLX7stb(k<~;5tMU^qi6q;k3)?$4d=MxoOlyw;sN=c*jb<_4llx%n$mo) zp_FgSldl+=O+rkHRQ3vubSZBYdKcGC>8#hc)tqIohFKmS zKl=PLRkX9Nq?5`B7w&jn3P4-6-90^9U8b#)1RCqtsC=!iAv!z&=U(vL;rnYCbEe)I z^E#@p`Su{YL-sj4i1bP)DH=LAsKbQT7OT$rj}9>c@pa{-1{!&!R}7|8%yM;|*MIC_CkWX# zAhc_8b81#SA#M+QOuy#*Q+B!M4=hqci1@&Wg+2`C{jTtgZug^hmY;n}?Q{i7&>S<3ipcrH_9S$NM3S!vNTIIN-yil|^c8q#&YO_iSsR^m59^jUDyLZLhvW$4k2ZBD>Kv z?Dh=_nIm{CY8|uiw#%pHnW5vBul^(?weF@;de&m)qSt=E8fU+Za3_&c(+k{~2xo3# znsW9k0WuBAi^{d1iQ-3*sha>IQGzxgzo$eB&{3^CSv@M^@HW{xo~11FL54$P^*oF9p9x`WI9Via8hkGMsY$Rn4Z<7tS6MxTL27P z1Ih&Xy22TmLQL+`&x;1l)jktQWDprFv_40(h#)6q-3WZVhok5!veus5=z%i*jwL_$ zNpy$@3y8QSl?jzKdmE2BWL1;1tbPMTBg*ph21-MpLqJ1-dkk0|f%BhWf#}UdP%GdO zGa;n8XCNkk)@`?uRDjF_;u0C94cF-N>tIlw@rU_-Q#kT}2=V5Gmy?LNb#|y%;Gpi# zwSA)&lJRhd<=Ly#o)Md9_@fb$!rBfdp0S|8Xl!l06E#e<0ydE(thhJk+;^Lfn^XVZ z>GZG#+XmJLyu&BXKdX9?;Q$r^+K;P4lGjk^svR)AToENgJ2Q0=+7>Bo(nMU^lEO3( zd6U@o^gcjtT#-C^x-3WZTr8#aNOVagC;f>>g&J9fttR4tsafRrYxGoZ>K{UlkoAQB z+#&0N(~9{)-s|6B!2ACIX!xQvSfta>u0;66O!5tl z-1D81di+_yN3%uTW_mO{wbE1BW?qlIq>Wxzt~(qP!%n zHN;LC3OcOY_uIL;**HWV@~J}Nb$@YHrQM$kYxRvA?i&1ImZ0klhjSl?udr*fZUw|5 z5hE_%Yku`n$aItH4O_IbAKXT1?dd`qj_TW*Fm_~OPM2d9pMSi!(#@a3pj5Jze0ON+ zTCLAE*kC6jNImf(9&u>oRM;#*aT?U*BXr^BgAU)OIW4k`Q&7QgPJ3VWob8V5*W%ea z8Gy&Z*K>qqqJVoEC43VA_ffR>&)K#KrgXspVm z-~IN`A;aa+hGVcApr;=D;8b)12Xv{f3nW84SDQ9_$ zq(4mkQxS_9Y#{xca`PHCh>8D>7|{0$4)hsDpgA|Wb%@{j?E8P83Ub?%ML;sQmMy!> zgC!s$&Cq`;b5MtxS~A7Dyd#X6)>mfvd1xl|Q#T1B12(BCr1%{j;*j)byAJFm3c-)1 zBuhk?#lnNxj@c)1Z-%KITv)I?Ko?4b4Ze{eVy5izRfQR!>0iA+0@eyBh$adi z!?ywCNys=s?e)BJvK}S}Dm`t`K`P)XEHHeKtwQWhA(wrfZxOhN;Kb2Ao|jpMM&yu? ziF?QELREC+D0b;@*%Iq~6N2n5w#a#Zc7_nN5li8or;w7#m3q}du^b<=STEEKhl6rBFU zRSOX#xMDVHJM#C`uRzA9HCf%#M-Gf7^EN6kFcAiA8njVsGEzwxzfEnpUZ5ul?z5%9yjbMi)&SFgK@!HLa}oA z3kYrC_PqD75?G5UrBwouMN?muf)^d5-Sn_4-^t^jV8e>ePCs8ryInY1OftK^BfE0cX3e@h z;%9i?Vo=Yuk^5~wZAzcckx+veOz>q5wu$-neL-m%|46C4|B0F62<}r9AK^;#CZqQ6Z~D^ZbT+*L6l&@Z|?f+);kGD$4DDk zn)hxQ=IRKWk6{Qf z^74_P!a>`}Y8lek&;&EN21t$nh41`i;clO4i?DS% z@jyJK4-q<9jv8~XZzv0r73BKFo86?du)E_e(1>D)?d6X8s7uCzS{h3+NL5RW<(-o% za)A94z&aE=37#%}NCWyEYo*spSU7Nn$!9rYF;&pd+`k_>`5`J(qdoG#M2nTIpmtO| zDyoi!cJ-7%p5&gdf1YP0FkW_<>u1>Y>=p=Nw1R}|Q_p{UBO{gBA zROgYi00@U-(P+B(}(^~BS z=7o0PNF!ea;DkM}RU02djSzlAX&pc2G{4+D0FLEuN=o|M(*hUf&fR5Lb% zyi31!mqrM3R+V4X#)|2W>|@NfW*A_3XjQqDNo|KdL?N~IZie1-WGEQIg$R7!+ptQe zYYp$HQyOxhm*+d)Oa1}BJ`zTYCdA-bRxHS9!(aPdH{AI{XayOB_l%N*r(Q5{0DFy7 zPk;u7>GU8^dC@xIcgO=o+x5is0 zQqQ?Y3v3yfZ;o1}H-ol2z1pouoD2 zF8MwhL8Zx?`|Rntkz;|o`J3?O#fBls5v!)53wO~D@(R7=VONS{vci#n&#mtlU$KZr zK&gUCRu880N=~<>wu*d1si9@aBWCCY4S+}qKp7xJ(J*K&!KcpP9nc?{dFv~uhn8(I zs7@gRo-SwhkG-2-GTIgd*EslwX<-h~2%KI{pIcM{>pu($44~PzHS5iWT-UI`O%p;+ zJ~Y#85C9R+*drOt(!X~kvK)oJ|Mah&IQi}4n|XZ!2#Vx$;*V!|$z!$-tm&qHqQD)p z?6_d4-R_R4eEN*wJQJ=BW_ z_KTcAK;1Jcq;+gwYd%}KnMsO=vYFgPnBAW=AAZaOvtdZHT?wPyzonYXXS z6mZ(Hxu*XCkmpP2-@gi7Mvm0`N0+qUZ zs#+$U6@!(FOjKW{@)Q7`;Qg0Q@SE!>A*1f!&FJ*%b^}H%B60zk136__Gp2P3Ouhz0 z?6+`~^_Ka#$K!0uyu?@%I3Rnv$?B?C)EFsD6QZ%QBi-RkE_o z7s2ix-W$pS`UeicW%r(^^*OgYPiF8;m0T6(r(^Vo3Wq&QcJ;mQ8BIKr|D6pi4=tgy zM$(6&KcSPSqBT1mVUIM1ifkAZ%0|CzU{ypt2_}`J7RqgKrY|Twbq&=K&SOU$MJ8S? zs(P-Ic^(!zBS)AftUn^7eu(>h`)H>)G~YhV^0wK&bt6w>`!RPnjq!#*M1!*}uDn-H zyj8@}r02kv7z6j$QungSWkdFv@OOUU+su0>4C%KY$Ga8^z z&*_W3TUg(^Jb`P+ran-SjSoXt)hwOeec#VE&U@wP;WN^@@2~&n(L+zUDe}5bkmj8n z7-!rrRIwU~oVPsFMUV<1Nw>~Cwf5S5?SMBDfdkflnRVj%-mumJu`DmPN4(!8ewjmO zP3@1~zpKy_w87bGQ%**9xqDDj;@@E0ry^j8z5}wOkF|?uU?bJ0Dy6S*S`5N5acvi) zE`@>shJJy)qxag#O!Oec&2!rt%4rJXqfh_QJ@r3V5RGWzAxx+p^tSISBCy}U6Ktju7ui>6|)_@lRpEQ2cJdV4ToC?X{xMMRn|-( zuOpKgrr5K3o#T=$#wFNQi?k{5T*V{?&oGZe-{JoP`G}2DvOERvhA93sZ`vyZK34AT zZd&@ak|jHN$iIsQB1P_lDFu}IqLjnbjmIOVh&`@%{(jKvVIYC?4#UB z4?r*Ifs8-*Y-{M;PauI?C)@ys5$YK;tZ=H$6Sf^bvWE>{g8g$e{&ixb`^~Qn z(M`y9GYL0FQ8IPIL2#v@3D7^AE6jg6g2sT>vnWLqS>gR@NxA3q`WkbX`VjrvJ!wBe zK$D{T=~TrGO+E{ey8)u<%W-IFh~b7YmWW^;G1%Swg?e*SsLtG1G`iTxPjoHion}m# zK7Ft*ATSQO^_W>~%GTvsmM@D+#d>x?cPdi8(#mc4(BC~juzUNVds8B0nF%r@rlCV# zi?_Ypb>1IGsSyD08@DKiQ+x2InL1B8JUgeCGYt$>DtufbT&PsX9_CYo3QY zy@i-c2+Y<%o#(Fbn=F>#y(?coUi`CAmu32Mcfo^%6F+`Yv*PN`K_IXKk9|OMF8x%C zrm3hsCNHtke@hf4+b@oob!LJ`Oe(>6Fj>aRwy@8=!5o0%|NeXT6Xg`t7$OHVIeA=H z_4IPXY{{HXMwwLCY&j1SjEjUJnF@9`aWe^{)snvPJZ?{%*ZYkcE|E)hGju=O|FO83 zF(l=7v53f^NfPW=f15=79Y(*zo}T?=YQ{@)02k2YMC}SlE*d1at%Hdw#I5fKWz+cz zn}xN*UO^%Vl4R0m!R+5M2bNJY(;+yF*MX_=88$E)sI2L$U{XAbKm;et6eHAv$l2_G zYZxv>2*e5}hW`7~`tXWFoO#Hj6~*cjuBwrw`7_0Jg3YV|XS3b9PuPx{-IWNEa}zZ* z6C|pfo~|W*J2Wgz?|G*eK12@CK5DOKZI+e=L&BgA*?$g({ya5$`x8(9*Pn$x=W-c) zqqQp>YEBD9=dA(shzSNrDL3oA|wyYi0Ypu7^;2G0(DQ$DYi#FgVNbSJsTs^;?dXf|&+ zG?p|;xQ4DaR+dEs45+cz~kHap81Qo6(q)PMvgbmmknMD1T_kspTUxhO{@?5T%r%dBGcOkOq{Cs=Bg&r=KX^yS z1SVX265_S3B7Ne^iAy7HTh#6h7E}`li2`!_#933ep5PJ23=wRL?48?gmCdsX6QdaX zT+NATR2ARg4@QfHfvn9JE8YS{ieDomjZ{gU?n;fbN7GI(lQO9<#h%-r!uzJ6)#x0s z48nFd_H?;D-Y&6C7mWAMxhNiR^?&hv&U|0ld(aIVORKGT09D$(<{-A#DZM{elKkg0 zB%_7H2Z$VS@D+0v*l88J{n0vDHrQWgA?SZ-`xgUmDmFiNfGMJuQ^rFqgA@ssStvt< z=c+BS4@id3Ueoa1(YIlEx9=a6K79M^3#@FKc8j&!7iEB!H>013d#5%bqJgOaO19e3 z@}rM}EUg42$lx0`j^p7&K22BWRz_a02?C?Cq+8Df8*aFT4+cV%!+pe&Xaqy&P_gW| zfcCvXZkCIa+bCG~5#PaCXIXD}T|0}zftaq=)Yf|N@TmUq-4-wyYQNFbfSCx~@68_m z=__8shtskEDon!fsT906$Rj8hoPSV!(DJOet%0tdiSd$8FN1_C;%W5$q})F!*Fbv2 z*8;*u=td=&lEeTsug>G&S&)pIL>H0sf_4`3BC|vb|tb|wx;wDhe z??QIOMZnsil^Tj{0$A@K6Zvdds|*wo&s@(MV4)9zZwD4cg@VWDza;+a%IObgu5HN& zBlR8b(J}j6UeJ=|*WZ5EP0q4TJDY`eIye+l4P3NjB!|L*y>aBU5e|hLRiDu?ha-I~ z9~HmhRyyQo47>J=iI zr$Mpb6Q|L!C1~4IUzzQm`%EAZfe#xBc0yP1z8;nt3V*{Zk!@1t3mLsc$@q(l9Tswxfe zG~>q$k_?+)MT$;!&Tme?|@UjYj1UvWZb zQPS~f5XY{t3i}Z(*b64X66hNRkAR>8_$wU#Oob8psH!{2R|U<-0;YkQ{#4aPI>oS) z((Rwyzu_VILb7!I*C`GOYP_oWkR5Lze&G)@=37oVor%5&-;A9GN8+_jrIYi4b5n3S%aGlXh z)N_BOBTAU!B-dpGxu#EFYi!5A4*szvnrw{a?{B;&?CfgO2dsHm$QEi#b+85q(k2&f zY=z_Frg^PoAn$>7;5~r}S1eqX+kQ{cLP;&eADM*APS~mY;9fzZsMMwmgJ(d#d3-&1~qpr_(VCxI=RHsaLR4gFogQ=6ljKVPi zG|O_YtQc87bNvITqDVzXSG3c}=--L&p17TC3bL5mZTMwN;iYlKV<<3s(XM1qze+nh zsG@s%tPB-Wy+7~nEY*u;uKrlNKNEQwaBg+03~fe{FlcA)4i;4DK6iv%UmAo;>!aU| zDF-nD&IY~D(lFi!Kz6?q=ZMYPPZ*23d28oTSQPSd=XOqgP)i@O2gfzaKi!u(FvmA% z)tqhG`{D(gRyF@tp^7mogV0Qd4-ikvHzjUIXXBMV`bVsr4 zU@WC>^^_d){agSV{k2wtaXP@MlXoHR4#Yxl$ZloSn=v_%3I`TWb1K%26fZ4NpD^## zdLriOXeW74BnJSC$@eq|USby3?y&gfiJcg09a$g?Wu%IxBxPGkYmvDL&fS6OO`p50 zF9e7RT5HFGHQsX_^D;pr3AoB}4YSh|rwEzg&%0e1bC*p)cr82%j#+?1fsBE#wo}>v z;tmDE16qRB&v7^DWq~2L#L-^)ifm)lOM$I zyr3?wX!_m|D83f2sfs{WrXcI$@L{l5#h{H*op&pB?PR2NJvnWe5$=LUIA~S-Oh<7n zWVsHw>)xMW(CZx|xlo1=B3KXQ@Q-!$!Z(XnCX@J;G9LgIgbn$4b|S595b6bfd!V$w zZVD>SMy*cl_~qMa93^h~vWO=OP~g25U?JkJ8{<|Dg6a$d%p4e+{*n`oCLGeR&N!lc z9|y6*8IVlJ!xNm_IEFK*JS0hU(Bpu(Q3mltq;Ehxqudl2kLINUi(L;!O&{w^AOU#c zlUK`5k_sfKC#J3WfB56`U00Zy*f)};^zq!ye*2G$p-Ut_NYm7&JM^O)|9h^QVHuYZ zCOX#hePQo?=gb&wmHU*XJoOcsnf+JAnT=OD-ub!h=Mty>Y3+(=6Re+DZRwzqFtX&F zsB~snznr<;*eG#(uRaw$SJHYrts)H*p2d=wL#$wyF@$iWM?k}|5rce$H77?5Wem`$ z9Pd0sKHv&j#PUu&CF58acf&G`H@)`4U$F2;#oaF7z!uytpU12vgWMasN zWGnIWipL+#S}-Hl=L(anY!^p7)K%`?R@!?KyY0!oJiab7zax1ORh^CtzJ7Jf%6|;1{mK+c>OM1e|B^p@HIs6JU^OQ{G4_+k!*1YNT5rF49sMxF$tD$nUt~`LT{%k;Iqy8XyjW+aZjf$Vmx= z-K&(ex_@Kd09c5=p+FCqVtDM%&rsPj9o4qjm>k{^NK>24A-7?=yO0LDmbA*UTtb5# zxb@xUK(je@8WGAZfFmeBJmg8o`)30o5-{ThqSSQWiLlehf1K%Str)nu(JK7hMfcT< zLPXv0vEpPzs*?za^9Iu~V+R2VL#Y~|0JXJVI8Y=XRVyeYPo{b1HBV6T_E`KAbVYF`8{`kqtTH4Qark=*w2EVnus{)Y#`4);6j%WkdNaZ-`(4 ze7dVGw>&$06+h&)JdV7ugbfGhG&%ir8uR~?WJ%b1ZpWAFW;wCIB8tw7_#Z*{>BlQh zVc@RVgr;^(r`8rhEf6^NKvYF#-xSuNnY*s~hM{ZpCOqnbdWj3S1p*3abr<;syJ{T0h2T$x#rMVjMZoV znGCh6Ch$4_-C6!@rWl879^;Ro=qoz0aDY}z9GJ@pBt+1$#^iu5yzDytqLnmZpCw-Z z`sVl#&Xvg#X&<&7rjj|S&yxI+tOTEYmOOmn#u)sx_IIgao$$s%SUUPdUD&pb+8=nc z!Jc5ABvVtT(?pu-9Rv#+}kbu4Or z6xoV^0f6&~S$$?hb0I;$vQX<3d49w?CNDjs{UCc)I*1hTCcyS?$~2cK<+=HYCH!XB z(%c|7skR=D(aBNXEL>-!C)b!};~!}Jf?UvHDj8Y~K3Lz9V_@kmR1 z)Hjl_^}R0#lg+6YmfTO7QdrZhsCO=B#igI<;@5u9)?~BAP)ss5DqjqpOA%yt4TwTX z9QFBXuxNwQW%rsJXekoC+Z;j#$XW7eU6~g=1v?to%6-4(*eOTARhP6yS11~CLd$y2 zrKeTH*8h+4+ZzVZ6rtt(+dwHteZ6cCb54Ee;5a>q#bt@%NKcI4Z*K7>AfFBH zz`6Ob(zt5wa(2F?42zumu(haMmy5LH9$u`Sd8`HO#8s8*MmhUK$TqFcyCPqmN=Jn7vUj zWm7V7T-Rtr1$&4p;W)#$t}BMMAKhdo2j=n4zhAdF>x~}9V0`$dT9k3gmv4h)PcAHl%2}n3Xtcr^U11WIksn<0?zYX{p;q$Y3K+?aV%LFCfDbHY zV7#Gc4J7G;5P|gzImFZxVTZoHaSoHxi7Tw%b%8f0%o)E+vc8u%Ag<59KWaxqDVXKI zauw!4eG>e`0C$JSnzU=$AjhCFI?iyEoTsqgXSZXlqHl-kZ@BkxS0b1bIL$moxNwkt zzZ~?XzAyjaM68vJ39>~_1%Rhkk@Fw`Y|m96CJ90pt{##ue9Bm#*B4ZHpUB9Bse+#s z$F!{tdJCudCcr);J)`bTo9tE)eI0KGn&MGPpJ+$41W+fxP-<*4#`AUgXx6%r2Uqf} z&7fYvVz2!*Pycu&H4Q30_6t}#3`T$UOo!~SU;Ax7nyr;oix4Mk<9Jeotd}u5r(cjL z;oWBvM%=>CK_s^YCA!p)`-{R{tR~}V4X|3X$R&(I2aH4q3ma%ZgeE4_f`){|P?erF znS1u7X4JrYL=vzJl}7cpdg(_qIj)OzG1NCYji5xgk)z`nf7<9%1!v6OaeFY%$U?-fa9GeYm-rT?)|OTXKkR== zYau|&vx##ckqn`y9?l73Kqu6ctq|)h5@Q)qz&S?G10Lclzk1tAeF0!W^xEaeHXpnI zprhN#r<|oE&Oe88j;}!<)4?Rc0xVRwke;sKl6&F=VAdh*b!j%kkC=;SV~A|Mc5Y9l zx9N$~t0w_Oe5Xn>%ZGGB!bo36TwvCj1!`f=5HBL>%jgKrx>Wm2S5OuzO59AU+ngc* zeIStkq#xZnLl6KjS%Ai5-w9dT7G^Vs;6#q13B*Y z>RjHPUEaTq@*efs2k<$tj1{nj%q}BJh?)=H(4k=2BCIL4Zb${F7D1?VU&<4naD3CU z&8WV(+N4(o2X)`WuvB#EfYzk%7*v`DBNv1p!#$iGfSM*pU>zjRAe(5wCQh&zZK!}C zJ-w7zwXmGH0hv-@iEWFwI~?;Yx74wV?P${VZw`4oef>m|NPzrkaWY6;SPl@5abnXM zr7?AQ4nqN|bg8b2ffps}=&z_9QQ0duV9}Ee{>m2G2M_@DYdkBkQmVyt;rBwCpbiKPNvZ;KMl5fhB$il(7}&(r1E02HtTIN&0N-Y76eK z>k)2h);nC9h^;&s_~2LZBcPhCkyNPqG~wZ-E>D}X%C-WwnIf&oKpjU2hSvQ)Rhn&( zAtl)J{Yw_Y6k6~B87Ngm7QiVr6YrJEK;r<+qH!Cg-j_4UE7W1S=&`3*D&kg%g}Nl) z#-(0QyieN|J$cWXClDzd9aR!|#^>^7oU?-NqVxt2a+nuo*wGmuG&z_0FfxE=QG z!FC>8mkv_c%J8Or*ow6|m0>wbq`5{9`pyv5{j)-dSONWmFN^vvaddcbNutZ8&@cqVvo+DVxLgooY7ysvG1^3W zU*e1-PKgol)YwsxPTT|X7@Xr)u?~KM&*fza6al7C zfq*^VZ$mEO9$sPp?W*#fr|Y+~z2l!5h+HB1{8dV) zGU(*{M{Wn_FNw2=_or+j7d&xY@`k6`WwQJDhb`W49cCY8(N09M^QSk*C3(ds{S1Ql z;O7p>g3BG^Wg?DwG9Q?wa5yfZ_EOV`P}i0eM}wC;F)K@=^MuG2cuG0h@{)asqACyV z8*ghO(0Y_3M1{dn4bTFT0eDTfIN}c-je;m;c?@&4hgLYWW&h*Y+bRNZs6EzSDXhnT zerpTj<6s0TMo9Ku#}Xg#j<5_xp1)Gh>_QtnrGdJ=5gBPQ2ld-Mz7!$C>xP&2J$II1 z+5ztvgmSVT@fRFaaR%RE?R^UePX-qr9P2wfH6=VsJRn@}3LfTSXVaD3Q}3EHKUe@R zpe4J5_CVSZXn8@ovKDz;(W0s^{Zky%S zM|or)%~9rCMNS}PxB5cwVc)%$t}Q>KinYJZgpq+?_r3(Pg7(@;bRH2DlRW^~zZ9+J zLQ?LpFt8FC#YOxgVV$Q?2kCE@VCmTt+5TSTDN*yGHicoct=%>9Zxzqhe??;)Yz8y! zHk-?9+< z_BP8jd@-cz5w7K=V8-4%2e;Z4ZDy6LC4aW6?_Df$iF$Y&$prd`?{-9JL03vqL(6x& z3$FmM{oAtc+^Dp994gUEVK6>yF0JUaw-S@G{q5w%HHe&mw}_MW4z~y000Jm2E-I=v zmQF9RFrG!8ct-?$m+C`{@BYYv&}t=Y2xB@j$&FK@r%m8w21VyUgtguw!}(uxbL{S% zKZv+^ijY=pt8E>2T-;00k|9R;M?;W(j1E(r5`on6@qgYSw_lzgRwP8#A+K|u$}@k7 zx--kw05yuq8y7_HHv2##ihRc@C7(N7*i|tzLk^M$oGm}_M3&|Xaraj3{Vgu-bd0r+ z8n!PMGd`fIMFTE{i?eK60zd#qsao}cXZP9Cr6Vz;$wbcA^*`$!Ah#LPWYY_O8mV%H zArR4>P17b|S7G0W)P}!NJ&jWg$RDrha!hbP3fkYv#ElnVxO~tW2l>9!4dxU`KpMwE#Qj^W9+pN* z2IIhZ$%*!SIHM0SNMGz&o8;f})Y5nYmSmyoy7IstAPWy&c1~n=dkPGpn_0I^IK2c@r@+JShUji)G?Z`|R&3rLaKih-Za6p-bpBXM%|91%wqKW*rG<;X zRB{r+wtHX2Ao}x0{oc|-$O4?|X>jSa2}~`xC5LUSe2a^aqkTY_kLp>)Fr~W1&S<+2 zO?t&t2CEg(ax6jZ6>I(h%?{I^h2$A@pbgBg`!}(|-p6|UzGydzedw&6nNQtfK0hhl zYcR=2LGB4QbS` zum;HYZ`_3)M6*oW*% zB-43w67BoKhcA_*JQ~41@zhD%5=P%OnmwAwJ_0LX342Eo)523SMDBOcgq2UalkK;B zz?#QV_la>(%MNHp66E2c>keWCR#i6t7;?BVqDPQ$e~y@Au4*NvsTh440RGO5g2zyM z@e}MjnCIYl-(3Cwz81%yeWS&(xL?5TJz0ey3s-n0@~!x_7GN^SX893aM7O!b01B%x zmSa@UICx9t)v)BF*=ph)0cpp{SuUqq9|!GZX$=a~gqt~H2`logkEBhZyD5m$26V36+>|x(sN+lVWLd1v>LPN>SpbW6UgnI zIDAE=4IqKxLGDyYA*kvqc0_{g@UiOH+s7798@i(iW$gH@dKkRFZ7^_*)@(1}GEhjr z%tpzoU~n|JYgGL{o_Vsfv_J-ek1G8#cMJoz`gwzCu$292&ndJ71VITC3C@{AjgXD&SEAcC|D;$X=4vsx95E{^8&61CQ6%(GG8PB&1*T@1M7_08JeLU zX}k1!GAf?i<8V*A=~`#={b5gs3<&?ze;@W@anjb?Lw#OM+I@KTw~4qy6D5b#u>j(M z-5kl-ouks<5Ao4#DtK{Cmj&F?$F;RSI%TcRv_$jbn}TjR5;gowol0VUJto z#d7%0ceb5$k7Mmo>W}vbR&f#X+iHB2ZpHaGWuU&2Zmw_Ir3xuLWwVjwf9$~nZiDr*&z}4&pGF$6%m== zecdBJLF6E}LjQXT$A6mazHJ0}FvPM4VweUIQRZ#ghM#s9l0o+Pm_v@m&IY8cDy2Gm z(O38#9!Wvji!Rr-bOuT>gdI6I5i9GzMXnL+GE8k{KA!XJ_gn-^CJLEyiJPjME01!2 z?rU35r|6Kbi>pfBp45GCbgt*5c+$(kFS#cz-npk@(s6^nB z7#udo7Dh~0Vd7}SfLhQMxygIHw$+ILq{PS)hBy8-eNS;75^2?y`@mHJj@UMjk$?(- z4Dtx{TEh2GQ-3+tb;-$Lb>V$zlZ-wEbm8NUy?yFhl+H0uAcepQR%Vik==36n3-Ko* zX^8Go2shemIg*FW5BcuQge%hjzTVnd(=J?Dz5QAD(P59s@q)EvX+$ZejM%*Tm+f5< z+f(H;JoMI~y$^D<8GGjL@(Lzg2k^dBza#(c4}4JD8lg}>Df^p**MTCm61acf*o=|B25uF*RCTIMg~D?hlmmCKx7iIi#Wsdvy^fr;tm z!jjWVD@hjm*|xS!PJDj&S2bUxIpiV6$E;7(}*3zT_l@Vqifg*_|dS|w=+RsJBYyG^1&Au=4WI>RSz$&`4O+p z=9vnmAT{BRo7(Rg9ta1W<9sI>J#|UP3rN(gBtSO|3R#>}EB$ zcj{N?VatMAJ=3}CYDX?8e`tN_(`7Vdape&5`8iqkp}TGP3jjpS&VpU@D6*A-?pl?9a&$Me=G^(Yy%VP`2F*w!wwH;|#aJ5N5Z|A$@xXKz`Zq-z zhQ-k2O%&Lb96b!D76BW{joSW0e6@-1{{D(h7sv;+f5s~y~Kicoy^rj2rx zj#6@rUm-`cx-!w4BdOjC_RVpZpNM*)Iy%I_-_SnrXhP7kWY1nuN-SrQ8Zx88_;+W# zO-Md&woTwejL3n!&kPUlcy=%!BpPcV9q6*keqE`{_Q>fQ;TBK0&Ih_Y`#N^CyC2(C zX5O^kzh4u^58+gAKX=gTVE*CMhhn(~73*Cso~(l_rS5yL|6s*uag+pC`vW(@ z5c18VHA5Ho?ZQsA{sOv$Oy}J%Gf#BMd-DBi+nn;)2av5_Nlx_mA&l2B3S}}W>|s2^ zDe2$cA@>I)V5X}s_xD*i;A7Z81aOYUaJ$yWPBY8NQ|2E6@+}|+$%o=gQY;gBy$sSW zdK0*6@ElIbogq4iCep~SY=A5>KqjE`yqJ+Tit`DEtkFR2v;hstV z%bhIliSg5X3Pxr$O{&~S1e&3`t4f!;u-H>mCfiWv&8AfmFf2`S5x#c?j^H(;@Ac;6 zH!AgF_(vCnO2IzB|19TcyvrD55g>z&$-k^{VyKl^^YW=B2RsX~2#fj4cjrPkx;G$3 zC((Ud9Gvir^Gk8v<=SiruK>j1+o;eDm?8wiQbQ^q|CZ`Ae3My6IDp z`G?8kI7S28+rW@Yzn3zziX9xBu)+7oMKt(o`_isi;;2>AN6N2QcUAvZz*Hk7(Fhr7Mwp zycK||sHDLjWr zCVU(n69zY1;eV8xh}QiIwLiVskzZ%yav`dD*vJj9Vpovp}bLUK{{_ z6fV2r)oCRz0g(vSCjw5h=hNfxKaYBZh%qOA`Yt1|A7E|P?4{FLc&G>!x>D7yU{VYk zzTYMvECxS=rdYD>xBcS!f3AP@2b$=CW@Ca`!F!|w`%4# z#izF*2Pb4$?`gJ?Ot7c+>49^|AxcDE(DZFyz%aBV_stYu19JwwT{;AjlnhcFx@Q1+ zvZpPg2&AQ<g2_|Dti3%hUE`t$zwy8EPvoHqI3whMs1<4FK(5cka_li6i zCgcuaeQ9UgrvAfgSzDpCjvCp=eywxe=;k8Y-57Sb&}X@-Kdr)LQ|t6mBgo)n{8_&4 z!?mSry{1g>18ovDBGap*Faz;=&-Q=7Y7$^@F~|#8`W4sqRP;9p zE3)L5lb>vLrZT`Um!$&FPsEhYT;6`M+J0?W zAZhZLJmW^!t&kzL!ksE$!$4o|%fHi~e|uqxO~W^$$~#j1W8ga6HCaOD%Pa1D=nEw3 zAp9jt%AJH@59lyW2Adv%0oRsz_RRJ@zy*s|q&<355Mu3}$4iNx^4&wQ;NXN;^`Rkb z_1&lcmUmMw=wl@cUVRA83SO;w$~fo3=Xz>90>6^(iZ^gR_9;NY3JxP-awjkZ+maxt|QwJ=iJ{uQkkAub%!=iNoT7 zaRVLBOt_4kuo&#eg60c5gAhaYnR>e-HMfeNzX1PqaRViO`vyR&_zY-YdjMuu7gLK? z2t_u$qwoRai*L?=U01+Iv$7fS(3t{h$HzQppjMdr9ILUkR0l%AY~uF%3=h0@)XUM4 z)hE891J%?ndN6}C*?7g#vHPhI`hAAK6eI3@=j~g7mWl(hTjre+1FprckRZl(MzDj< zUcn%A0xkI9=m}lN=P`o3X%=f3@q4}1l-Ou=oGXSRggo+AEFYki1AHqElkBxP=0Lpj zq9?e;@m`gqk(;(g3I|XnN;N27j87D@)>MxOZlK3989TYC`r_Sm;`cXbjJgNt6*Sod z2y@;uLRm7A+d#4K43IFOy|;FqQljG~;fW?|*E`b`+Q_+9M6LJ%I`a3GKH8*nPZ(%> z|CntggS-tff^A3suI>7ogbyk6&SOOmS!jjS&~_{W4ymJYEME0mruMjtPywwwc>Yeu zN^8_Tg3oj{wvowPmUa_+6Z`ilEvZBR9vmI^Qcx$Ufql0Jvcoje59H(U^R+*b9kzyx zGsn0hA*!!@!Sga~4lYCD%vPiNbQsBbT)?L0ASR_IZQ%Wb^=t*bI( z3jYh{W2P$$Q@Qh53g;Vq`~-K8$q{0N``c*$c&tx`{#? z?TWf3c4j{2CjnfjHTii__u!l4koPf9%tu$WN^}Iw@QcjhQBwmi5dWfw?DzdZ?Ud+X z3|fxa!NEXa2)P1Ho|?_Mmf1BFuZ5_3LRRTvOaDnggJ67s$ny@edK8y7eE zo_CXhl8>UqP2dQS|L&L24N}VzaUbv>DuP6MnL`}~eR!nA?Bx~wSTJ=FUGV7jr@Iqea_ zbNK>70Xzd9yaL#L1&4K=ZtIG+kYo~d#I1YTT@gHLJ&0mfJ0*t6Ih?&Y@RXgh3XHUV zlK|g7Z)oP_=e|1_!>e#X^tSZJ(M_yMiN4o8*)u@^-f1`uC^_I^Kz12EsTVHC6F2WM z>6-Iu^pJ(IuD54Wv~#sdO+Z{xuz0v%p4@KF!f{JBw9#037+I3~T3~*{`83wu-G&UE zh!>>qco1{~bFh!rL2yJBJ9qYKUQtrJ9SD^RFGwI^AFi+x`}InjxtyHZWw`c80SA*I ztG+NollF8f*3$|YY=J7FlbmvN79STVWX}D-L*imeNBb!YT91a4ZXn|Ts09Mzwa+ZB zHpG-fyxR>Ozglhn*OQptLaTemFprvj!-(5*I5Fo9nNv$XH53Hal~!+^IBWXn2YGsy zR`{RDWh(x?_D^`r*~tMFhe5MndQkl6$xl1(!YFh@wY0FUp>OV`Q7;?4p{&jG-qo_D zu3#n$V3IwYGn!z6Aq<%<=uL!N`p1h+o63-`C!8#r?OQNT%L~!&efp(nuO&nGDo$t` zS|(889L>m_7B)2vy}-KLrNUk+7;o7MBSU5L_b0v;k5udH`pLgDm$B_D=FU&+ioWTM zU?=z~1Yhr+rrz$>M1g7BA1i)u zdA(P6Yvt}4ioe8aFfGrL6%!u%crDpI40H(qfeZH9v%d!6Y?!;#a}n4ZP~!63DHuK{ z&v}2KlHH;te;)rpiI8~((DS$!Kjq;FF>Harg56tXlw;hxi8LE2?32E|#A%l!k`|fd zF3zeZ9mCJ51<@9xU5G+gm{Sue;)oT8um1k(7##8emuHor5lgm2;{ezBo*>9DOVXL7 z;j9=Aj7<(h0_GNW818LaG#mKIAOmBqkU!+)W^NfT<6NHGqdCGG%SN-kV`AnEeJ}V9 zDm2lqRNY@%Jd2Bv08J1&K!Ed`!Fycg%ZDuE7b`YEH=E3;z)?RR^Y*809DTRv<5(GJ z7KTi=+H5$}2464a9{x6>M{}>eV`}EmdFdQ(Sor>xD9plCqXq%Ugjr9k*s&149Pa9w7H~BC`K5to|qE(_~;u{I=ieV@LYl zYdqu6gAt8ryD3vx!_1vnTy4`a+%&=wHm>_O1mhA6X-**QparL}+Yw`^4!8oA`$BG3tEYx-t#jO{{@`g4x1_houSzuU_qgU3|XVjaX|aW7(!%GY*2b-T?{K8uMV z62Vnx|I_#$>GYV-LHGeb=`$})IP{(&e)xKHv^%|efWUdAQKG18pABYr!Ikn20vb5g z%cDMtkHof_-$KT_)&1&!Snu1q{1~kWcBmsN`bt0^N2+hb9nSfyVjMQ>L+7l3@C|Gt zafP$>cOhom20n}p*u2|*0 zEh&5+CAJ3+XoTZ1mxy|!Kbip#m|I_a%uBV$xSEG+YPV)qpIEpi=kY8(tT7I*iZ=wLmLYJfX-r8NRU!9G#EU{lH;G!KjOR zxr_V4s7e=Sl3TM4lN*O6x<0J=Eh2f={jei{*Mx_V-KUrAR1qaqaKApeGpH-8rhV)- zt5ln7F;BSzHxu=BE6<;v#Pi+Ji>~VSXoq_K_Ii3a@Vyv$rj|1dvEgbsbE}kQ?pzx= z2z}D3@5J|`dM8EmC;acM1n7cQvN+Ok;cbafBT6q1@#Ilxxh-$x$sp=jyQtH{pc3l(h7{{Z)oC%)fIB+ zz#c4gqJ>C(+a4@j)O7gBVTLfU_`!B2`NX+lSbHzyFzF%O2Tu$WD)(;mDg4Wp91y!i zwxMtn-~s)ptNkinTt&CNA%mNF=l+x3<8P^aq};^=LS+mbE+$=PTit%r5yf%n&{lMK zTFNf!cb$HvwO?MWrL%~O2-@5F`zsl=tPwRuEITJtu7Ry&e39RfPeZ{~QN*B=+2@o9 z>&22Ozh+mEsc?K5V!X_w0{Kc?;HVlJ%=&Tm*8%WI^wbVtIS;utzy!MkSJux$+B+te~HO&)M0cPzpOY7j@E>l|R|b9r1;UjtA2 ztd7YQh|UaCF(*#LJv_Azz}gV#Kv9`zvp-dW3}1SQDAHK$=L~@L1(1hBG~yUQE5^JM z=7XH?kbp5_Qk8MhT|9-rBX#{;L1)YX;+h~IPmMVn;J`S^4;pw$B2Ih^z#fW~Dpu(=D+LhiN7t; zAYJ_3-1uS8>ZyKho1<1L?f?jS?KkeP!(bQ0pnOxA@2zD!!5BbI(|KQv68KQ?{M|;u z%24owngjt8cQ0N*NweXJKH+AowaJhcxlp8h11kj079f?o_a<#6C+mnhF3h$?;au?~ z$OItnBd9}+fw>~*P#YVk7-3RS7wmPnkBm@fCB}|nF7I@gRBJJ3yJ{Hjg}0biJ%VP zGJxa!t2Z^!(VLUPiLEI<#!-+BXoXNd4}Ix+{5&JzFGHPx~M z-Oo**{p2>Pd|7`gI3>YLw+{3VuBCIP#{7hrz~XVmv>$E^CK>VXt-%#qddT9GJQ*n2 zL4?gF%}E&|iJpKyV_g)EoG(7kP;Ml-{)*S=R%t4?FxpaT>V{*Pt)!lDf6Ghm2>imy zTVQ(fx|$`5EvG1v!Vyg>mb*M^D)xknI?OPB`C!`}02MUSNAQ14eG6QS+5dkwE50rx z?QXTwAjGaMxm8pTTWeTWtlf>Twn33ymo9GARu8f&(nMB>1|hpHi6z&jq^48`q1>8k zs?oh^n&$razt1!I{{FAii<)_!b3W&DKcDkCpYzRid`4Q+n^=+Qw+v~^BQKj`aJf_n zo*ehPwU&+3ml@@D_<*cSyA6%hed9dJbiA}DRIbltC$C^EQ?!_J zV!chMGs>T<>K#dzBU-;Gr>t?;%wq66%Yfq!2AiJJ#qs6A_H1ea0h~GYlc;j#Pnq&7Jhxw zXMGo|RWteLUxMbaoLBc6UYNpuuXXeP2s3HV>(A3CqrkQB0ZRQ<`U*yp?K}9b@u*le z-cZR5r>iMzN)*y$nv}((!p-Zsk{wJXfysBl?4n%V|4}c{`YTL`&`wd0PgyjeggzJ) zO>OK3i#5p_*zcJTb!p!TVfSwAAigQy5PZjVa5 zagFCU#>L-83pGbgn&Xn=>^vU3KPQ&IAB0^$^oFv*p=nJtw&nr_EbX$fP74UVEb0i_ zx>MFL><9QDN`t88Yn`yhX-};1iwMRkeR}w2#b}F$4f|Eu%G-=$Kb)N%wUp#K4l=5A zPrnE-LktSM+p*PdTBrF)bU*|csYbE1>D8vP`pMB(nPK0{#DXrwRB%_;_5)3VcgP+f zDkH-FyjbCjTO)`#YHZr5fR4r3@|k0cgGBqmBL zEH%*xf+29B{mlfQE5f=(;>p3`c#Qp7$@Du6{mB@}L`eDi#(~STCE)ByX}OhacFNkV zn?riLfundr1Kl(amVvZ4Pl z$<|0oRX7;t9KD6ty*^_h_;N#nhIG|JJ|jkeTa!mZjS-vMI=(E6El}m`{XvBpJ|xx!`8WGd28h zVJ{ai*-ep?3TTm|wd}q&%n+9ZS=n|pBo#O;64s4?bB+9z2$z`eJ){l8U3c>`6ZAor z1tJHDuCu)Sd$$I+&v66`s7yO`RIG~@y~+~HN{(C8BAZ%VqQolqM3F_8kXxJW zUCUWKtF!w=zBYM*m>GX!CoI@RdX5EA?N3|35|~#$ZIn!tT!3GV%nryq&M@U*UNEPJ7`JqqR1zqgj)MUw%bNKRjll~FwA1$k< z9z0&hlR(A0vjE?#`}P*(7u6Fx&iT4}QV155T7ERtcv^ z{XSr{fdBYDyDh_Mpdx2Y)12X%FfHt@)wDf(6Cb^{_11AFn^)DN9NYbns|;gjmQcDo zu)UnZjH!zgc`sL)GEttMaA9^x*!S~$*KAAtXt%FUong9V1jRkxcnf;3bk1`m=z$b6 zA!C1{U+0{m3h>v*d#vU`XJV}fGCn|hd0e5bP(mEw6XDplVY?>*gN=e-fT|;b@b;-0 zfnPR(6*}$h!rj+cG)!uZTKarVS!MZVTk%bcv1g-wmHG`v!S32Z51w=JHhQaWrKi_2 z?7%z42KGMrE3EW7O6XUw-MclKOM2n9Pd}y9sw4l;WwO5;@{+Ik$|2U3zEpU=EH$6( z5pmRlVa`bukAp_$Z3@RSP`*8gcr{$)#+{QKA6Zy3{GLgzJDURnIGU!}GlRw-~9OF~s;u zUT*V`5y^%}W@FR3i!(+%+94vaL#TGu=d*CFR*x9gE;{;&1FHcxtap=q5lk&tS~9o7 z^nr1EhYM9ZA8jx)B@^hEGqgS{ZU+_p%X?iME$u$d?L7$WwXNO%*$1;BI1V?6+s?s7 z7{#fhu62KHsABFzjp{0h5;H~HAuKRCc~lL8pM;lcsHso0OLxvDpHr`IdvvFJQ7%js zK}6g>>anH0>oEHZ!(Bd@&1WTBV>Th_zAw>N3Wl>Hb{ZyE)&Q!IrY!d2WI@)nHJ6M# zxh)A*SwqGSahKzp(q`>3RK_LzSG!H|NkmCK*o{xzq}HSxz4T7{U)F@_7ww3l8ba`0 zq={O&o`1L)uqbR6%S&?jZT=ad0`=FGf=2pBO3FoO7q9)sv*~Tb5l))V7J!gEl6l!3 ze3vZBGRZ_)*opX4s5S~})p(9~4P|)^`10BHksqMySGybYqG{h&1`~OY>t{=52Wr_1 zdDEqvq*GgcuAuWE9Tb-_?{da?KD?ZDs?z@nxam9!_DpT6z!u z+jLOSlea-EUq4e7UCjUA+ICe>meF_UIP>SBIF?RyHv;z0MkX+)P%~~3eP&Htn5^OB z{Rm!m#(!zTNQI11n-J1Wq77&UuUCnt(@rRL@cx>e`)~dxXAG)DH0{88+|`qw&sl;T^iONA&u-_-@+yky|#2eA&_$ zV!>Y)Jvo3Rg0S5eJ=GEsSL|3cSwMSEg(| zip}QziXPQnV?~niR*8A3onKEL=Tdj!mG^fx=MEYnJ~W$tTR4&0k-d*eTi;(ZBy^py zPM|lb_pQi-<^dMOsr8bcNS1#9M}~kpN9XXq6BeAOMja2xNnk`>pGEs=UImh=K@EsA zo5Nlj_9#noBt2cy?>L2np`r}tVCPF)dU9}Ne5>lJMcV^UFabhRI^RpBvupd2(j;(4 zHlA|aLD(X8@wBR*rhsC%wF&lvGMSg6*A7jJm(mmslWDDamGfxAXkE;|3$BZC?N<)H zZQEb%+n$Quk0;xu%x-k3cl|aAE}Aj(dGuCAgg#SCvOsD)qIlfXFgQkg!P#j8!tZBd z_XPxN^NCNIBBJ&Sd;h|D9xWqu`tMX(WjmNtio-H)vnI{k5o~Cn^C+pPX>EI;;2k-& zUnsnwKHV-bM^ue;?VCLKc}ZWm*+S-`~@81G2mB9xJf+!u5Yt8(p4y^gnwMu~nPGX_v+fi5Gawal#R~G+($uza}V( zvAb;a72=Fgx%cF+wU#Bc$1xvY&DZN|qrM1eyTlxKFd8y&rSV@-I9=%nj@Fg`;CFCN zY^?38q_dM3SuRaeO$SSUsuOVQ=G5AT(pdmcC3@ZLZPGc$3!j(_-0L%AMTADL={-7Z zc(Ep*$(#GgtUs3!8k}7dGtBdyueR^;F4fs5qPgDeR&n?APy6gZ>^1HV!{-bh!l1D; z@;AIm+E4{wV+teSf0dE|8IRsY%!lga$0|a)B=ha=^jt>6WH092q8|VRlE~tqQQ$Fx zNzbU{Ar?Ku+{5CGW!soYDr|Av{9}f-8^|Q5bJiKL(zMN%nSb>;JHpLi%20 z)MghRq??tw5o2y0)om7m?l|F?RX#MUPit-&m>77_6dI?o42s!2tAv`=O;?B;Aq-ud zU(ZYWZe5j*TgIhWvFEln7(|)-577XX53ULV2a%zji`N-l{r1mbZ2L(N(z6iuQmwkJ z#}ukj)1wj|$@jlGOn>ui^g_d1)N@jb?$dWPqKH_l5MQn;*28=9_z@HLjX2VIQ<6MU z!1p@o=PNw-IJD`2uch0$qF5`2`~INT#Q{cwb7UMlCn%!maflvf!({)!@li5{IX4{y z+#Pz0;jhNHL=TVoc+xxYMexYeHrml6=o^fNg)~suS?XV9Iz0&2;MuC#tGVH0J?x`V z@~N;Yy4Zey<|rp~+jVEAT9wET-b~28=?xkVKGf*Gn0GAI8NBd#m(l(T6(s11;@-`& zejfvhbvlC4frj2=bY8#(b{m55jc&^JDhL;$f+z;+9K;|i)}f+0(;uK;o=Y-OJ+Myo z@4qym693ApuILq;dbZRb_Wi`fPZ5pHU5i&Zce|2jB}RGtn1naZ*xP-frku%sOxG9u zqyKxIIV#>A%~nRx-v4w<=fnRj4nh4I8SC9$Nj#K6h=(?z70x|Tf%)m&KH`RLTr<($ z^fi0iDiMY5gzYe-2%c0NCf|^4_xNAUgG~!wLVLMPKJT1=87ow^+m_ee{85ga6r#s( z`~`U*mNI~661cKT6#B`!UhqFabDfqfV9p{}ea>5Fc4=0aWYd&%KO{t76vg@;(T2l| zbl-Ddyionf=3143rQcCp>z7>9%QB%w`q^m-09sk;#0VUN$#&2?ed#+y)i;VUI67 zFtuUIKC>^CbMPAEeq-#yO9@R=vB%lk{4)_G#@f*K1Ll|yq*VJt{at#fa}cyVc5P(} zvRhb}Ul~pGM<*y|MrZBCwWsVk6uk}033&CM;?|zct)?^n`XNEZUvRLIPKvppzRR!1 zT!vQ5HTL`e?p3c~o>FZNWYpq->tQn_tRi}?qc3--y(o0{9dm1K(wU7_DUr+#E%3%u zhi`cwoL(1oxpG&<^-HdVx*pB+Bu z0sk*r1e|1_ZiOQjvq;ohXhc}hlX6p8rpeyzf0=}(-7fcfx5OH%*x@3Iu67z)UKAUy8a4j~Dwks>PvO1Ozt5eDI1B^OD)YA~VBA4-v~6%x!eYHj)K zY`|GxW$U;V*XLM`3CP?Jtz zdNY0(Yj_8{jL~-zRoqd}mFb@@>|cuG2oHFQnOJ^{7)yAIvKM$LZ1a{~$9LZW)|c z_|8bLsyUCucmW99*z9Z1a#Rg9t&TO8SSihi?iI}k0gHW6njh;83XIq~w^b$hm z?E8N`Jv+at6+;BVWWss*YauzSq!;hCQ9gBPuKQZ9fwKD-eAGMK=$|ZIH{5|4hU~Z3 zh>c(gWEz{Hv#uN)zp6^oYwYLT*dZ|Q}oq&PMJcLPvDxw(!GDi zdav`}i({L|l_jdO1leEZ^`(-d3rAC}c0a=~n={rEY;B5{+C_epP}hcyQR_X3EfVw& z{OoJU9<=Lj~kGdWK>M@y?=)lS|u{K!80-!N}w!dr)w3tzr z%st3Va0XOD^gry>7Eadyd!GJ~ND_@v0DNS>j;)&e6Zv{2k-5P5W9IL8 zgot$&eLv5?Jk|L}>^{MT@cVl*%pMN!q1E3x-dk#i0EkHHC2FUnCple>T!k+?c0Rjj zLLgauHnb-YcD$2(PNJJfQc^?&nfRM85Wb}zKx+OhWP6ku#IEz#g$Qx~7s>TL;v{_2 zbDeCr>&0oDg{fY12Z|+ReSwu%tkO7%GCySbc3LDO$@TwW2G^i7o?E!>ke3-(NTRDR zxq~upBTtse?G?dq@wzUXT00W)#fLZg{Iw0E-dyP3W#VOAMgsi<;%{Iyq}C+c)+Y}Y z5;0H<%!d1jh-QN&`i1(_yzhI(aGZJbHvOT~S(>me){6PutK>Zi;2w7LXd{+=0_FW* z=C-?xOcFhyi5af7h{L!D$@ran_yf11rNKe4%CxA*k**ZWq#c~Oh*;;8I9M*d%ZREB z!`$B1M*9m7N%q=!UQZb`pMx_k;5YkQ;hV(;*vq8}r+(JZax+jkLoA1fMAbOmNxn$s z%})b?5Szjpj90Rbc|kM{_|>?2*j27eH%);Lv2CHtNYl?rj7q_KnVnm&)h_yAc7kZG z*nqoX!h)|vc{AoyVlm9tVGc5En;oxCB*;IT%iI<`A{-H@Zy(jlvSfgE3~u6v3tXIytQ_ELre z?~31@iEr8nd_1`(ZJ??l(WBVmkT3(qYeGcCm+W-ua#kLR!k-~4?TI>R>t|g zatp7!(X<9tr@rLh3Q>m6XR-KRo|3~ZN)-G~4}%GSynr-vY!krYO%U<+)PcBE1Z>=r z*g*kT(%vf@UUP)x*Uy>mcdJ5qPJ`SPC>+q`rvWkC!qR7OV9{@D;4EXq(eQZ4syOEF z%;mK~;7h9t=jIjIJ*=NE zF&?0W$1Tpjo3|w``<+KI)%40H9ZHN_Ti>0$r&tk|@-uxncFhMf+czWtc;lamJyjim5K5*HKt8c@F<-oulN<2eVW0St&*jiworREjVfCeK%ww5GMhA9ppTo zzKwqUY2JB@*JAUA2*X8qLG+b;KcdXgIOz`;53VJlu5Rb=Mm<<_A3}fvS52|Lw!Mk6 zHWFn92{r`KFUN5~I(8k0o{bkjf*d{V%>NZ!*qLyR3u;a_Azcxbl_FCVXu#E`WF2*E19rMha?;&W6W6KJ1{=wQ@_jLH_=P*UEofe zx@a3CIj5q{I-jgfTNjlax%5QnfLiZwYOY#F!CCuR`0l?$H_8fq8}n$IE~`5kiy z`T}jQkA_|+J`@6s=W5Gi*O`{%FI7QuS8>ljQEouDmS~RTMX*ccG1!La8!Qzt^qQe$ zDAr?0IJ$VY2qA0&e!+>g!>H<@%EcPm{l0@ z;OpA%5Ed=>ehggu{^1x7q|zA0_P6>)d1GlWgZ(E%u5-e}Dg=2|XXoAAMGp4?;i^?% zIVkN!lP15KwR=ZDGdCrTCpz_N+0xCtdiP!4N&HTl^z13v0h1FUQ?4m?C3D2ul>3`GA*Dbq+mHFtNDe5K z38uGYta#*=SrWd=t;n8zy(TvE{QKk;%df)|3fuuwcTsoi+MjYmNIwCi_<8tS+?q$pWR__+6Qjo||I}h_s<~Q{N0dMkw1Y zD~X=wg~dmNN!qG|lmRAA>>7hy091OgEq`{5btN;Z4;xz=y#?j>oK`j}`i z!;QeH{oXY5v3_y|`O0k7t0yL}8#BpIo2{d7eAg+59~;O#!}^BmbP@(-N*1OW8JV!P z0qVl_$nvfgd1;qK>dB`Zm<j1)iPJLqF zEWM^aaY8Eu7(d-kHb$XIC$(<1Q`rvenH~e?sD=(;ygOQ4V7;R6fA_}|bHh^7YlR|3 zSO$B2i7-%r-GHl~MBCF9OW{T`{3ccYcmGo|yAvy{nxS;VKIu;ro~%Bzl1G6WNbXQF z%GS(|t>**c2&77*R-y4po`Z~|BgONaPWcH$%pfx$!$o9wH*-!L!m9HZiT)XHT=6I# zkE@c9FgbRHbYjY?^$*$TEBe%3irDKic|AJ!c`Dc52eN5^Qp9pvI( zk!$0u`KqIy@5R~|cb3X36O)aX@a4#@{_A#msuF2YoM$c{(!dKX26SQho>j zai{T5yftfo#saSQB>KG%t7Mn%>gj6VE@V@B#HvMW=iwPt{x2wAb~o8qMQ3NGQJPbr z8}at&W71o2pKh%^WH)c7Cx=A*JEU;dT8RSK0ff=yfrM2y&+RA5ZM*OLh>i>hjaOy72)<(Dx!>K}x4dDQS zY^oHy88+AIJb6pPcG(CquM<}4@xg?&2CTsyr!i?bQd>KtB&xQGU5==fNYqXXN%^G)c+us6;=3uZnfqAHH8ho3I58{R|c{u@I%9UCF~}z3lpd z-NBnA(D(1fbv%~azx?=M1aqA0XqX)BCHQ+4i4&5xccSKhUxTD#EfR(-*opfGh)hx| zPj+#$>MPPVxN@~V%b~cF)KY@^rm}ubdZ*0A{3t}5qZVlt{k8=Y^A}5Z+8=6hX)ybb zX{{vd4&E8G>x?sE{ifj>Y$Rv(eS5q-$48I6S3AHTYOE-~rK3&5w(3Ttesm5T*E@E9 zVc0%O{#GtD9WyLEyX$g|sEvM2-#fU~BQFlb+n+r0TobO{iq#WtQ)mH3?#8m*${nPn zHuM8CksJ)6z&zywk{SwLh|U_+n`;(nreV;5QHDD@v-AbLx=;58CdcLp77DCaCdIAn zJ>=f-f_M$J&MTjkoiA@V)XUnFt(B4MGo zFXNh+uB#EZLa2%OYh%|@J6Pu7sMC}D2rkkt9x0zXPB0-G_(heYkp~zW3qb5P-Ex;1 zCa?8o5oRB-dwO_D_zoR-I+`e=t1Yq2*`8QxQIGZL>T@#ind#dR; z^Xtq|T6}?yOQEGOCIQ09>&BFf{r12X&7ZVi(<~~`#qz#zzs}x`o2G|6B0oB)J#9A! zL4GyngU}YOE;9m*3Q!_v><6=%%cM&M+^R}rLqhv!pLVFou7oR|Z8YA>SkFss#-Y@@ zW|!g!~}nqjk^XSs*e}2GI(G$x#eFxp;B) z;^j$^{S0MkGrap$%}{-gwS5&EJfFY+wmXEaf{Qi0rj5m0`dI z3L~WHE7VgznRy&)KO!4%mwTX)FezfA+mPj9!gsM z3sn$E(kU@z%kC*@muMWwB>pg9vpaZlzr%e_K1L8vTb5vHZ_V~^8w5xIsO>cnPkF}6d>susq z(=AeF%9AMs%ee9_qqOVjA{=oelix?zc+3E@yFQAOx>$;j&bVc8Gq`1v-pPBmi+l!(OUXA_ zf1WOw)bXws3uksiC7PPFgbF#!)Aa%zco9>#&8Dj>jdh0{g(UI-UU*Wc%^cyJPgHAV z;S0mrErGJCUCh>o6Iu9#bg}~`;a)%d@sL3y=n(zH!bjXiH=<( zs*1AvBh=eqZ%XP*9tek-?~NoQPqE}NHCPeY3QbK@#f&H zqK=*yM%Gjr%r6#QcaoGad?D5Dt5ZkvYvMhjp)T?$W$1#EnOkpIo?ha{LNcgacu2G zqqKHFyvA2ot=xRzVc;~uu2jh2N_qEn=Cj~rZ$qiXF0-UJVrTY`L37OfT(O4vcC}!_ zWa(w0QPqswB&Gqew~FD@SsVxLiF9gP>TC)T8G;@_BKq_{Q{WIH6PZ4F;x@}2D6mLh z-P~CiUqo3a>3mogRFX~OpG_2_314;ZYK(An4yt!44akDiR#Hut>WfdZpi|aGu+FBD( zdXfx?gu(Pgqtl`%AI#PccO(ulZum}nFu~#Z8p8lHQXK2u*HDnyQMc=Nz7yZ>VzlJK zk{T+%lt|a^c1B2yKbY~n2>)T5^pq2{P_Pk1Ut@6fbIu*+TR$>eGj0T3ZP5@~NcpB9 zXUwgMr}632753$FPhqFswPqvf5Us-H8vUSc5lwmpThB24Ry)i_^AVY=8+%<>9b>YK zg*5!`I@h1@XlM5YlwCcOIyCfm>R0a-s;oB|{|z{@F- zXoUolwt(XU0zA6umq9^m0}j@aaB>leCxTplc)>2`jmZgIV0{$aX>J&nzos7qg=F|& ze7+S&$GGe~_K#cB+?e3!Xl!bTp9W`Kq89iC!nW1q?FPoH zS<`@VnnWxKe$9#Q&)(f|ky}igi1K)={dBT=Cr$papNFEvC-7TQtrLksu`M_&S^5n< z8=QbgK4+A}-MY3G2N|CU;v4Q9=*E1T%HK+TSttdngR(obpqvP@W|^2WYO3nFW_w3z zGIgSss!EL?^~cf=X5pX}!Cdq$5hhBSPVo`NcsFtrxyXdH;^nCR!%uXd; zCGNAMdH17tSZ6``dd~YsPV4J5uQnC^t3%JF+Gzgv4`w8A9gn_?>e60Yn5sM7L+1lR ziV$8U2F`F|IVx|`Sa=&{!ro#0+_L>09t3J2tKubZ^CCXJIx^K^;=6p2TCkMS0J6o) z*M6yXJp94z?oV^LPv#S2Q87qnJComhKjx0w*(kXc8~Zi(vr~K`OFgP&?JmO&2KaFT zRZ>ux-)r8v$S(TK*svAACW0N@F3x}nOI!g9OGkhCq%}%TuU%i9&_CLG$<(@(zBQS} z->xXX0QkvISCf7bnHriVI>!Kv4t^FM4g-4e$u7Yey@5ocEs!GzUYts9|G74 zLsA&A)63lRsyR*(<8S&IHGQD_7Sk#)Z^h7OQw_M#5QYguI-e0oh7n)tnCVHmqdQ#y z6L2pA$UsrlZ|j_!a}kdK*~JT!PqSpHe`~47u%zW5YfI!px3QRNb^1ZdvTVG)RmUL4 zx0FYV*JcwYOt!yb4OZ%{bU~g(L5Aa-zEeqc6>OTURs^A_Cr$+7*_&*6z@W;Cuohf$ zrm&3t9L{m-(}vzVCzct`@fEIb7;VH+dDo*E#;?4wdUIa-;ULY1u!;WV3N_5T|$AY@y)e=zzgBdzmwy+4(3a#jLCLhz1IQFm3wt2Up*` zT(mifev1JhBv#WTniY}%--|21#~<117DB!PJV7iB^dDwl-44Mge1Imo`bCioOw_cL zr?&{bX+ZGBf1gA=bE2%9P7G+pb_(9@w4RvI7seMiO-qoZ5*~nuzeQDB_o|hTpaXW# zI{jw%hyOsLFWH7quWYs7cG-KrfV|CZA0?`bm8!vRn9=NE=^ln%+%6#*zt_|8yUKQE zb&@>58JPUF_3DsiDGBCcbNKuAxr}C3PrVXCbm=MtE-wCwj^&G}Tcu~=W7&IeUU@iV zTj;}>XSbukCXh6lQNf=W`*xldXA*%7ly!aF&z$%Nv^u>$nDsd#eX@6lAVgjUdI}b% zg@8J7$WheuJS>(bpZn243HRYQym8wm*=~=0U<0;KvGl3Wz=-RkBBF-ml>yvB)BQ%fzLT4-QeEC3hoguELJGe6{dxp-o56KkO+L=gLvC zhJ{c;5z3GjxE&?yN-df8opgPOTCA1QpLdAkreNN20*Rm%so_V~bKNX-MMu>UpWHgl zUR@6%dGI4M9Mo8 z+Zg!Cd@#tg>)L1VX+sRX-$Ci}aWmI)f9e4!Hf`W0!M>(ew!izXb)^rgrVvRZm?@t`e6h=jBHP~aG%;>bLgi?e!o=*hUv1Uvp33m>;c89!amG;{tQ5 zIqtF3PCmVGEJoT&0{>OU1`F>o1*XAtWwMY;(+;h=)YyMD0-vA~=;YF)xbqKIpzMZA zN&I(%e%?h3NlZe~8rtkqcc9Ihl()li)JwZmC@@J{xAt`Im6IRLHvgDr_+czvE!Fqv zw$P+EXrQ>cpNhyVkjU&A^*+w3NW;3h^t}{!hsr0hi=BXk2Ya9w?nP~1xDbRF5${TG zw(RddtQhxB-uwBy+p*Mz`owOcQ(zPr(ebcEg|`W9RgORWdt}Z-6EFU|gA~a$gf*G{ zbo(P0#pE%5&rm+y@mx zU>?-=5gLeZ?5X7+|N4!2cArla=Eom1FCmLJOsA3Tz;-|RISSb)PsZ-EKRz2ryn$2L zh-pciu6%8pzGOw!#@Qk4Sp2SA-G9^qGtTp!fSXVI(|Nw|APZ%8PNcNd zje3|EnFn!OWk~*^`{3ykfqpI-98Z`iYcJr9diN9WZ14yY43B`uiuluw^-xf*`963> zI$5`CAKVX877{av&bs_=xS8A(q-o7bI#-$pThCHaSHJiTg*BQOc&fb}*eh-L=FYL3 zp9Ka=OoL4+%N>7^o%?_hIUPKG08itF1P;A8&cW^;a85eO^9;y6pLU&wC5Qm-+XCYL zcH1&=VU>-$WwqCmN2JtcHyx@=CK)r$VBU{*6B zIIp)l=oPAeEF0KxEIV|S;6hqG#AY9zm5pk6$>sEV^|j;I^Gm)~p7x>Pu1HfQ`x4x) zb6P@=KIFE3O|`pYr_(K1@UFMrYvLA0L;xC+B)hqtx&RlC+_(_Jj}zqXjy+W@qF~{u zPLH@Y@CzQJ3baAR6WqfO?Am$Typ=KGE`o`djURK|?`MhLlHfu9&mIXcsra9GofLs2 zxYM#dd+vK&voP_Qa!mtw4}D+<%Mr|rGOlU?bAm_|H(8nX-6ktlRTp-f%bIej?^~q2~7~#;7EfRV$>hQN&QWeR3R>}qH{G(oUwoX;p z@{4ViV;l|Ud#6%t9y0ubJr(dqac~9a(<$(tmRO+6 z&q**C&0sUZS12Kmc6A48Z(rh@I5%Fdkot|Fiv-D@1a^=11|b0g=1n@3P-Gc-S%-;L z^N`$1TGyU7frH(uaxR=XZiDXn^5(SGj>aCkZnt-Aq2X=8GzfMvlK;iN-(q zD^0JBN@F`TMordFaQde(etLM|XS+@62iLhBwE!f&f@S;n+b^F}Dv4ER1uU*B?ojyK0k4pV zAuRk8#EJku#!54(EV16^SB(ibjHvU;%oi*az*t_?;)%(DEwqz;rpGF(-2d6z&Hij2 zVdVYE_s7}^_nsr(F

na0mB=-EWLNsEKuPj;S~NtDH1%YEn#4;prAfBdnS!o?Xnf zK7Pd?1H^;Mr!=x?jX{%JU9flDBR>Y-D#%Or9lU;YD}FotlO5&RdJk!qeDUIoPTqgO zMWM*Fbme)npj18?z5Q1);WV^lp^k@4 zJesOs`xBL|>j>?C>HD`<3k!f_AT}?=ocQ7I$RySbFe)rl(^val_Z$Fq7i7@-|LtK)Z8{F4& z3XMVvj#M61v*ZNF(e;`~WVRBaCs!mysu?GI=7>XIxL%L!*1H4S2X_ z@U&bv`;B~!hoDs(8!KwvS{$!8lC|yc4bv?&JQ9*EOnPeCl^{$~y)BjbWj-w`CL551 zXSN2--$alNWk%GyB5>pnTVv~c>x748vnGVQwWBC^JZ(GDe5vEVwJ|>SsF;4Rc z$OON^Ug-y682}&%;>Qh7L`nu>L#~|Oe&^7v69*jUumonMR{GOZuI`59HXu zxBb6tAA=VpP){whE{OA{E}B^)nC$S2*r+f`BsoqE;7B;Xo&3U89}%)tG{1KP-IDOv z>%Ms3k-x|XrXJzR9Jy#RZzM(p&#dCqoL#kW+2Oqa>Q%){U1Tpz6JY<1ZH#|~2TewP z&BIMSQD??Cv;30kzJ>fR1bS?SRlmC*urN)B^NU>kJ&NN9oemu?)`_#_<3LnXlq+X+ zEZqi-K-JaH4mFYZ->`Kqg=4(Y4cdMS?IA}am`R;%=SAXLWKCq$+8t7#b^nA_DH9=u z{wFlt9pr2=po$&AK84x7@(GGIXKv6pCCQe7!fq~>T~e8z9AVsNk!m_>4M9Bie6)8cJ2Qts#39I)lN*Yj|Ve^V5Y9&;|~z@ zqunSRoR*bh_2lvLdEe*c*M?)x_oCd^gdUm@D{LW4O+~ z%Wp@WD310C_l%)P@JM*BDq}D+jLt8%O52Iy$_vj_P`6MqpH~DAEQ{nZRa5qP4uO6w!jz^&-_U+ z*btalOb%?|02+NIfuC$ECL)5SIJ&}1*wv4*$T}G#sv;)>TA2|4F#UpY?7i_g2w%l% zy8nxFJBjaT{IC5zoRvs@ z?N4xyBzf_;wUgJ4>vN7K#xIR`dQZw_fuOp4y=G^MekW#$J7Bq;kN+JQIU01Oa40}5 zP@Ng{g@qno&}+gcSF`^mP6yEzhU%Y&J|@?XK2^I!A>^{UkN1Du>lQTZ>5vn#gQ_#N zxIjjwWbOqfySNA!xx_IQf5zOv4ZuVZs_G88{KXq%r_<5@75SD`DGjG53hvb1HNNft zh_4u9Mi-Uu{b1J4gD#PFaazjy34|)5h4=d8A8bN=fZ*@^m=!zh9d@kUlN?>|(Uv&C z$RR>sB-^vvW82SSdveIs?+Q1Fqp|z8k$zF)I@q47Ceye_@9_cOo1r`U7y1=8G^17S zv=rx8(=-$m(TaKJXd<8pEEJZ#{9tydj@b>r9! z>!&hiCtvrL0gBqZW*2wDEzQyMt`^};nYGyP>@5ge_&bt>gB4D@h zO8Sc!XwoG_CyI!2upfE`#-02Lr>RulJ7wJrr|&r2P8X(-F;_&MOSj)t^@oTE1Gb7I z=p#{+v-Bg5)G>`Irz`{|Qn=eKF2=hnxjPq#Zyg$gj-Vg+3zb>QCU;X5rz}1Qr>_Q!7~*s8qLAo4?rPf z?d**mJo9fSzUH7r0?|gVJwL|1Jp)cH#dJvPiax@9zEzoU`RUt8gQ!q~xTJjd+@5jt z(-}SvS$RJvTIyFa~+v9HXl?y_>XPVO?16S z3oF0Jmt9sw4X|`UXgu)aM4QqHbmOxLn~-T#H>~3IKmoDUE!v`nT?l$37hjI$*P#ni zr3k_cLKzx=L_$7vC{Y5a{l>nl54Z;VfaOjOX2&^(tqa1DwQ;@d6?Wv;6E}ZA&+OE9 zJ>hjwwI*Vcu!CW-xd}GijCCSs)G5VC#ZxVT5(H~|MV->n*rSr;isl`-2HleR14D1V zxAIQ~7JCx-CECj6;#=&34%*akN2fmDFqXud&^*7U%~=Ww)JKzDxGglrp6F2uOPjPg z#;@TXAjxB5F@HZBY_4%GJT$;jX}?!gG@@X+HNcLZrnXc5m~jiF7WH6kvU`M=Jn<1 zR|#D-&^3=5wcl>hh2;G7=Jjqi5E-Q}r=Az20;R--+q?cD3SMvs zuw^ep^Oo6n#uthH7CjA`$-O`!3j!e0f-)3QDSNpm z`U+w3!f{DS8(l`jgwyY>pjO5J#HslO6T&%ZjwAsH~ZQ?WS(`<<4$>&$f zxa2sE1ip7m)S_j|IrJ{iFWeqhHN;R^gd2q^2UK@?bpohqfQUN{)@Y;$p)a8&zxNw|7Fe8d>F|qt0%#jbNnUkeQ?7NGewxP^|CfHUI#VXVW##mB%6OI+|lcL_xg40=FA= z*gT3EZE4Mfx{*~EQrYGfWGkX!5s57Cui!L3WVU|C1W-~~q02qOJsdKea%?&BHlZZY zc|=nykwH8zdGfH#sZa|T(7IN?Vjl(YzNwGKJZZ?|P(ppFQQDIC_O6Ip=#|xNf#C$5 z<1$mvJ>aD?qW0x*vwEL=eCkVN(iIL`Z^=qE8f#?wClZT%bWfKrE=Y(Az z{en$uvu(=O9}nl2Z;Ic~WE#tY2u~hM^KN(uHiZd}=n3AFuc7|(Gkn^d=e6S8NI`d- zl@nDcQ;<~8$Xm1Q+-4=Mu-G**3d;Gp;95}?Le7wx*CJN&qDb=u*3G1sCFYDOQP7wIkyp`&&g_V(T|!pcg(j%QSTmd zeL+YP5X+1H&6hiy!-}{Imt$Kp^WczDi*?mW=C}AIM^wG((#~ znq2lTqKfRFBKaVHvJ%kjpnv*c=GVYsyH^yu&VM$qx*MBrJ2Gc5Uq(F+9zZ4CUvcSY zF2$N9JAHh0^0WpLlpn(Dj#pt{pccAp%AZ@S*sTrl)O*jZqI72y<|b>?*t9>WEw?42 zWu%nY$w9p`ORIU_VSjDmr$v)n*Q90orb)C z%rhst%Lgl)1UOpBIfDHSf`N>sDwhnGcREp8<$fGGK>DBr>l`u1ly6c zk{@2re4t{D;M7L{GSH9Jvo=*I}F~LkdNiaVLOLg>rK*rX6lNEHcrkdYv#G z3w9z#`03Ke8Ef5VqGq7&Jk<6lVkAC);+|*#1)V|T4V1Bdp*Y0v?2hJi!J+w4s0Jo} zH_ZQF_Ddl$h6MU0f_$-rebLY3BDjxS{+t|ayO8ZlFFxWq$>g!rP-jEUJOnEC^UQzy z#s>(p%8jT=(~sqX9dF`$=2-U7HSW$jiDo##8)@m?*wQ2|HlV*~$i;4|eejE)bZzoy z)P7XEwQ9z)Uour0D7HUA9tv+vvxM&rT|>xhD-;KSjp4oP1~%?I^7`-(2$;+Oo9go9 zIDuG{woTi6j;|YRQ~xe3IYjw@Pbv}i?zMzx;AmLjtUd@jD+4CS?%;Io2J&k>bb(Vu zjoVTa4OzB4<7Et(Bc5y+l6Ex8E^zBvYSsY==}&+BIP!Gt4>BrgX;YmhUYnouUS3eS zE`R(_fld(y*r3(87-gRA(IBxLbuF{?ilQX(g`!dUZ8My^G;&F{3W~9?dtUB-WfI(w z+n~csRS%B-vuL(9861?AdM_jg&Ph|2(3GRzNMoLqde^rBUmO3iutTIc)`z}uy0tg+ zL`0DLC!=kn%#o=T!GTFitv6((pkj?ij+0Y8Q45}5GY{-wFCf8$7Nj@V87;_Q7oRos zF!w%~oy;uiHnd>{G>Aib!+z0c;_ww#jh1{9j znql`U(8~h)fr!(?L!UxX-it&zCzJAnw}VLD{{Tbmmulq+Yk zb4c&fIQ!RdXLq$m{n+mWT}a%kmIncQ4pb2-nXhX9!d^HL&WJO7EBkv6T! zs`j(3X|;TV6=MwF8g0+fiE$P{tTj$uH6@QZzH;0knZbiFEv!&agB^0l*$~&C2Yqr) z0#8*($3vyDVU3>VqBK`a3WmWn@7SG_?~lWVU0Hk7QDY$(owP@mWMh*w?e&q^1(cxD zeqiDoAA2)Q@rtp^X6FyIH=_|rUL3wzYxpyg?F^bJzVdQr%2POd7gM&7X)#a#F`;yw z`PNLU=!5Wt8eN9F zT6TKsxFFAcVZoY^~Ghxo~!qcIEIWWyRdlE#8Kx4iEmJcIJqT7@8DwQW%_A$ zR$?Pc7?9~G^7sF~43<BI{-+7VvDB|iLmLzax{ zl-XE%?MPdkK{mI;~m_2c8X0n6F1gx5Q z5YZCIK;IIxD$Tf>R%5s~HJDjMk#H*-e~{w#oyo@@ie6P;Ei-OBr&V+|ouD5kIWSj6 ztR#2Q-(>{pr{oOc?dZ9i-TP-tPGkJdsoo(Cl1hVfA3v)!<<&ZWABl4o`+={&bj-7+ zzw|X($b$sLj{~mTW%jORPb$F*EMCvAH>q5Gom$Sg9DqDa^rc4@JYEyf)Y2ouJ~a{( zr3fG9i9loXO6x~ub~6_nSfb^GsqDcApFn<1YNYJr^*#592UoM;qxxloX^1J*WMs0M zcmFf{>7_#@ewCZw0gqsv^lnePuAq0^2Qk#;!~0;sDZOmDhUF3P(5jA)i3h> zl()(8s~*2T&fAqz-Sgu{d#}-ew7!9j-yw*>=nM8tx?+z$QhBY~lJ)HoBST74pp1AP zl44yhHQRYClAMm&r-v9R{6{i*RWT5HUi9(dDQ*?bfJ^5M#a~;r%cp8+J01{u8ebuG z*>k`Hj!30I9VB#)7d3kUvbzAbf06Vy4weYM*cNBRe;}r&-yy*cO=eoL!4Lj=Y9r*I z?aKGv=3^4zY>FdQlJ9;&bVDwZjpa~EsawSYLw_;fSQ z-CMrZ9vX5CRZJ-+_P#*$rH=vlfs52o*ZKTtL<^nPv;F)5^N3mtoF_zvotk$#@w_3( zAn1fy%|r5n)CYDSu~8YT-;x8{^dda=_S0Ox*Q$xB1A1sM~E$ zDm+fmC~Xx@cK1nxt{$l9q0?c<{t$v+J*PfHbC%X`cv8yL&WfZUI6;4&UTSz`(a&px z3DE3&1BNTx@TV}xmha-*0-{=Y^YGT@cnt+27XJbP9@<>gAtV+FP_`O(#3k=h{=ulz zZ~!$qk}vx#Q;{puin+C`1kFO-1#s!wkKF7Ci3g4ro6J4<8Hd1Ui=(d_KYzz+2WtYX zIKm)tK%?JlLsCU974=Yqi{J-?R=dlYlbuF=^kKk%h+x^&ICgn^n*$a9=QNSOo2dc1 zHc|)}Im%FlV|w`&v-vTqCA|)_(sym6OSp2{$c*;7w7H~Q23~j#(+9Sv>pJG^5sH_1 zGQfKyAbp6l=+VT>JpFDMoeKg$8a<{A8>8MqTbj3B?y9k*jD~#Gq;>ac4|m{C*+4qQ z)_&Ju!Vx4DMWP#%;YE%5>Q1TUH0jf$%f9U7F%>1`8QpHgvPk2W<4r}@n@>|hcp>o-toNxb* zn@2MT$GkPb`r+nX_arF#0-zvYPhNX}!bnYy;|G?WKRe4SWMIdKU;WK>HzN3(wU;WH zdG_2>n?55XoOr;PXQnq2q5pvC4#Z+e$OI_=4)rFlV(FyAAC_;}5s!js0PEA@p0DOE z?plTeqtIYHjf{bD%A zuK3;1Ll%p7p(+TyExe1@cOmKrGT{k)VxhHr=IVA_-j1>j^rW-5<~yH!lokvCHr`C2 zNSmb-n(6_^a7MeI+xHm^{9E$k-&4{8*&Fu14x>V&~DKepIfPr!`q{0ife);R3pwSGgPswgxdsmolt zrc0<2@H@HVKF<#3$k_%AGPaoCt=;D(a22_aI_B0_y3>j|OznVICU490?s3XL>S(A8 z<5*-ZrYRj;9#Q1jvIf`+9<%aQRaLtY?`w(@Ii5zdONHN39ckV7 zLM2eP5P5H!ae?I)rz>VZW9?ipgoE1$f8*V(7w_1Hp4%@fRvdV&CKkP}@ z{V*j;0_6O@;Syv|8Ww^ui5?LEVWsB;>iI~hWQ6ADNIh4ryh16n_k~3ZfW^)pePE>h zB36`)zn`!sJZuUnzwr{^V@$=P`v*SyjB+@|prfYBADzVB30R-nE=B!qVl;AtB+9=6 zx;rWwhC`l3J)oE0I42<$d;b7eveaH}&|Wt;`M#Mdl+baorO^}KfhqxR;p}*9yJaBA z_I!yT1M35@i{9*Z%qfwGpgrj=3YpLVr*(9sP2P?}axWmSIFjT3Mo(HZZ%sH=rv1eh z(xkf7&X}no$XviJ`f*t1Ty)v(S*qoi*QKr;0PNuWpG`_umj^838t{6Y1%S~MFGFDm zr2djO?7;VUNoi123>6{0XJ!70aEu(@;tILk!)Z+!e~yU`&h~Y5HE5xDwAzfTXZ#>< zG5N^8Y(Oc=v}P%mv=MvH??;0&xihP1o#dn0iHb*|eRq6d+bgEJS#E9xa|S5IRJWsO z8~p`ZiPZ8%6V>GrnGT~mUpansnq30?23e1FRTJWrFZi%mRtpX)?7BIDx=@m<9)A{Q zC1K!)tZ;OKeb_Br%!9UWSD65Y9d&rYhQuJUmgN6qpY3_p`&G-BXaO=snJmH~)xzSr zz|l*A#7g^OcFBShDF(!0{hlzlAlKz&+?uo=d(!7XThDlemm%u;c`WGR1fReER=Q7X zLcIWIH!XU24L?O_Lk<_jpZZq?p-U=vi>&ff0G-=cBS2Bo=$?=qL2%YG&X2Hv;;HFr zrPm;t%ONrcnmyLn|%=}C%(#zNdnm*!7WImU{>Qturs`I&ef-a8i zWAOS-&3bEgslEhXdf!QO4cbyR*5=1!0XPJA5gloDw)K*xqkh;kL)kWI>vXee`_wb- zHw6arcEGjZ%IcNJpej)jqA_5Q>4F<~iQqsl6X-voaH|0+$U@YQN`3N1v~t5Ootl`z!WWgX3wk4DK0Wr~CQ zlQ}ni1`qlDs4x7|++IS`U_`U9aH67StbJs|020=Jo7jMH>s+=m|A5 zZ>n-0e6$aW8qbC(91fE(x>>!THo}$Q;Lj^VGOz|24O$99&eaAkZ-l#%(M#k&xX4-h zW5^#MKuO@HYVVMZJAu&V-dB}B!k*PUg!U<0<9Q^i=z*`4~DueB7kis#5yCl zyR3*g;y>=$P1P+nS~{=cI;1~y-qOmySpOChZos{+8u~C1G7*F?zvAj24FE1mH} znneBgA=R2Qq)egpua(qV#&GJPgc`&JCN|k12z!Tsg`Rqs>yvF6Jxz+w9TPJ9Ua<3j z%$*vy|F{b#v`xnH4b|b15q>%T{XYqn4S-XiAwwn1=r(-(?yTz=R`3D?$kZSS%S*o! z&CtBhf4d8kT~E@2AAD5$s}OwAW<%xweHV}NK2s>$&1D~1mxMGoJiQc(IO~R2U+D2_ zj4CdU3DGji=@!RR*?GJ%ikM_uFW=RvLu-P4?~CS}k+so;8E8hxlvYXp<^~YP1Fwgdk_b{jW5nFJ?$} zsJwClauJiR0@213TTdMB?b039leo#owRW_R@wQ|P0os;veD_Saz9XNc#F*331tgNg zmU+#Y5cMDceswW{m)>M z{%>+(V#MQty!Y`5r(VGu9#h>N6izzchONuX6-CY)$O>KyvCCi=S}MZ zL47=@&^*wY_vE{Oi2}ihpwA+6a3ush0oaWWH@c)C86oiO8mfwngy{lx#_Ksyr$TxR zjTmzMLqw4G*avwA249PTUB071TJBf(^%w<%F@NvpRRD4M27#Gk1gn4{(RGG{N&B@J zj3Xx#*DQzZX&G?W;1WU>%+B4;S(`E33R@U|IW5OaEgFTzOhtYn9bVF*%jA*g2w{!u zI|_OIKEwP`aPSyu>N2)uEK6G=%16EBzn|G1s3pntX2Nq;U>8_15R;>M?e!P-&l3Cj z=v=_v1bQ<>=&*8Fdp^H*fQfzw-vU*T-nPdXXFg;d1n;;lN^jM%g;&bIxmR>U7KKQX zm-FyIjx;!nG734h$e@$@4o4Y%97)E06T&Osc5c;ywQ!eMK8>&}$N$Dq%8sJ>vE6oN zLQaf!FSySDQk0Kc*hm3X!sS;&54be&o^5$45-KbU7zTQKF`~d8!mvWM=zWZyH`(x* z5re$5#}~?W7tUOeYan27YuR__(k(Xw42@;Gs}AfDsm>8RJ(|ufwSFftLL2jwuIz#K zscw@gt7Tb{-uJfIvR;c(;B!>e>;KxTIkk|M9zVV_&`#bQ26BIM=49;En}U_ey3UH#a`n{(7xzn_3W45EDj^%wnv<|3si z{j~{E0<@{6kpqsZ7%Q$uyRcR}S_M9|&+eS3;iB?grO-R27l+-&#$Qq`DX8<0*XRk( ztUMFf+=bdQF!V&4=dQtoHZnQ?oh+QzK#XteeXLA{MBCjx7kP7~Op@q?+=1ph+M`*A zS}H9j2NQR4qO@PlBm`s-*gT$=!GQO+tReLcEIZjyq~dBw8W;Tl#0U_Ak-Mj0y-t^* z@!T?R_b}QF43>AMd;OJ=Kfm zm|t-IK=bAlb5=vS>lNLH+|`rUg?w0G5Y8nN{cgyNXitAyu|HlsB>7#yLe38%wk3nH zZTGXNYRC#MttA@~A+mV%t$tGqvPk~e0D{Jdu;2#{fRaV|c>3R;mo(w8a-{=MWWP^YzciOt?w!8ijlQ6Or6))B~HE6$Rp@pd@ z4(cU>T((TSBX>?aQt>z8zQ#oG^N-w;BkbQARPYg%7XdwS6(3~!XW3T|7paNZ%GIhA zCks`E(y}oy-lc-!a^v$BDM3L4@isR3N&aBM!tF4Gx7rX*(E5FKjkgR3wL0I^w)WHK zvRVbK(G!7pqpn&d3>B%)L?U>X?q2lkeh(5^#o-(4?+4B7NW94!9Mw~q)8*O0G(fys9;E@Bo z+uJzpsxE&fsMHgTYMe!z;adTzD2>*cypv$>prhyGJy^RZ=h9!C!|>3d-dAgMFZm-F zsx1cI&fhZU9VH(&TZTHBc2}#1ayls-8GP1?vRVHbSmJjxK)19th90+3@idaNtIVw& zPb^74BG>)kyw?0-TI+gp(rxOP{_^!m(sp!5CWr!+grN8FPBez+sNT!{{Azy{}KlaD$E@GVHBmI%(dYkRepdbfMSkx0$yed;ms{nnp# zj!s*OVX(gdTTc@fjs!A!IATOW#SSmV?`OZC`hx+J&nI6Sy#8?3I*~%J7M;{Bg{elV zBkFAbLJoyoqY#|W{+eUOxCE%+W|`f)A${5qK8S@|r0m5@XDQ;58(Frd`p6W{?>4Oc zf4vj{ZN4y43ZPiYjq1LV?ZXwR@$+@bOHRF^RY9!-T&{cF*siA~AAUvEno4bhrk3X= z1>KkzJBz_Pk29~)XOc5ic=?!)_2-D`rrx&{+y#==8}fcjJd*V~8-uy}u3HIq5b#K1 z9?w{|da7gAcwVOJ;sVR?D(zopq_d~nI?zov@9t7Q!1g$ah6oa@yDoxx@jpBNxjIlr zNOr#RhP(yXLX%?dhJ}}fMA!jczhL?^=KL)4hy&{Yoll4&;i`9$44fp=&rK|9k%}Wn zK+StS9l&cxu$OeT%?fkYSh~5MJbqmT2KE0^iUXnyBQQA0{y_7F%a4{qb9eNxmpvgn zbLW?Dyl!O*6=TJm-;;jq(>gHj6J{!Plk`~BJ>!2wrbU0Y4eF%Y%GJ|$>4J38@MMq! z5nAex4>-gDrtac@2ID;foW`VSCw>9mrr*^1Y2!bbslL)rMKD^MIi;Dx0#Kdw|EMQY zSZicZ5#&?ZlEF(*oi zX+!<6EXVU%W}p1mYg}mz1Z78g-SQe*e(bjqjQZ10PDQpfWoRghVj5Su$c?ec&pWAb z&Gvj6El#%&Xxsm6c%=U(n=RDk4Ndla9|)#QFj^+VE$mY>>jqXiTIxm#C5TP{t3TNH z*J>UYdgM8T)XOGh-DEgR_MPNPi22l6)qp(WRK@=o+%AAo=%4h95rW#~7rk>Ffc zsYs&EIk+U}TL*<*D-#?H2pQ0;sxYk8#!q4}n|Q(Nh%s_&*(e?b9FKcZ<1G!>3R(=I_tBmW5%GWD0caP4 z*zgyTj9mA{{~}n&-4I8-3x+M_Grt zmP7jl?2I>pGV*<0x4OQX?VoVl3n+q`t=yg31)>+y^pWr1WGAnTsrRZu$Q!&|C|jXZkp~Hc2QWUgXpst2C93f&c=h0VCFBEqvdrl~nGV47S)Z_(;L}9yUSz!;zE2#bhVsR3`761tF{}YAJtiZ==6AGg$u-ewhJaiLE!X7EcQ0)b4UXKR-m&k3E%Hk4 zEuLj60bd~@%)fY)i)=FBBvTc2(P^W98Z>n(`^>XzGyT&O7E-OkAr^S%ji3(hrY{Lv=ro`t z68XHmJ6>vG4 z=pbP5$kkd}IFV?VV}ovfjR*ZYg*=jElIezNw5bz>TskQLy5g@S6{Nav6gBxLuOZR& zp1pjMB;NJUWke}ZCIJ=d9uNQNbUYgaA{?bO6Ls-4Utm4<# zWrw^dTTk#2m7qzN_>rIlU>YGHz)*j%Pb1(QAX79mk-IaEoGH~U^h9?d{??VJo=oyU z!~-vxBmSTmYI?~ji&T#fdL*vf8O|L`pQk9PyvuQH@uA(PH@il4j(;4bH=mch+}XW? zPU+~+DXE^*M2Kw?=0%L_S<&cj9OW84Z35NU>m&oYB)YBK>R#GxP6hoYz8P$cvgcqV zn-BlC;bBSuqZWdR46H!_g(FT(!8 za7YEB^kfApgTWxI*tI>X1(Nt0TX=ihnY>S0r@^M|uk~5qE!hTHB>}8_dGuQ~aiU&>Rd~n^p9fT%%c_dszTGi^4 z$tkn1ue=97#@YrQH@59oR1+))?R!9zm^plYR=D;9(f-Gdn*n}DxEn3+P?sCplK?DL zh^L&H^!jAngmPAfv2pNhEqR6vNV|wM9e>q!R@oPiI;v1t9g=o8we1WQ#nT+T3yh_JndO;#RobOc=hW*(hCgw1V3pnl@3FxLlByxlCpz&p9Ph(FoPS%@tR8J zMSwn+HOhVdWGP!uZMBnx!-7^=E8>QrLYqI>A^RFg!{)_0H@k3QYSJ1L`v#pF7h@k) zCYgJloY*wu$YeaTb|<)U*=|4CnoTo$zn{wX=EKHidS{Wq+u4km^xP5alBj1Gq)l~m z6Df_y(e+U6}1WntGVu4c5Xr1ITY z#LXdzt5BqV{w$OhmZ}0mg8cHclhhoXT-F4457t$$g=BVBab%{+n$NF-Mrnmjd$dMQTVFrR^x*B6f|3iLf9zOm z7VEUH^7B>u2-*0OWMeuuE$~&_3~b@pb8>kz0Y!%J_?r(mF!XZilV+6@3oW#3cR~p% z27nG{y?4LvF)wOPY{b2j&aZHoqBHqu-%kcj7mSOeb>=Z}GTMqC-cytHwmWe9)auD= z{ycL4J8z2MMvdg0yD}hdBkCZZPDb#gv<(rHARW>Rp#<70zX?oANGev51pxiqKbY*e zZfmo8CoF)1T*BfxGb@ZYH;3mzPa+|3uH5wfw>`zbSO+XhBq_&hv?e&l47~>$7bspD z+PPD%@s;V|J;Y1aMhlE|{wN&8wsGVe>HLPvL`tY({$9!EczF{)W)KAdP}xC}qJ<## zwV(pL6{Y6PH%<4yzS0Ym0|pv759goN`=6}_Mc-Fr#neI(_19@%CZ5TbdpEqU2QGYC^`{L6cF34K4gwh z;69(H@3)hsMJ+`CwOY1*Yj(N!p$ef z8m%U>i20F7b<&wVU$5ob|ELA+O%AigyZga>XM{)cKUR0^a66>!3c{Db%Sl^;8cAzo zBDgf@G~Ke$n@#q|Ng%XNn!SSUUy&Wm>y&7(QBd_M7wa9od6Z(HyzkKN18oA1rw%-; zWSh=^1D&GxpIUw8uc0O8wA!S`Q+ReA?j;q>ce{B<$U4y2(D6(LQ2vJ)@^OA{DIW#- z-~^_fQJmxKzoxRq8sReH&YN0P>*_W~{N{sh^OA7)R4=#3{k%45RryR>KEQ=xT+91;dQ zv_lbO?yM#h76GpMJI@~;EoVWa_;HIfW`bHp&$%girjKwCw2@2R87WWzT!v;4OB2U54F~ieL&~es#j(`Ip8fhF28&l-M z5GtdVBz!36GXA2P_GDbHE)3T1SdnHQN+9y65LbCU3_ZEwQb>pAUND@g-(k49aqRa5 z1}TLADReOy4vX4M=SeYC5dal(yz4G@4`>5BK)}Oa=aakuvpP@02rjtw1$iCRHgq3) z)wFz7UqddA8jQftaFdQCf)>n$skcFX_Sd&PT&uqT{{6@K)#E=&uLa_G;o_t~BV>>qi zYzMSrumEuKQD04Y^CYT_vV7C`$#T6h)me5c$x~dVe_)BJ%)C4ZS_1-v+mh~RUe3l5 zZx=Uq99eS0*4QQWWfc#sVQL18j&P6@xj0HpuFizV8U$ZpXufJOSV31IAd5}bXF24OW zxx2)G#vC?A8$Q;s`>Je_S#6K%9=x36~>n@L{i%X2GmJLuROL787e_TNK_mP#cbd`4^4}B zdccku?I7ACRev6%4X{w^YiFz07NCSmcOm(}{K0x1f%PM3R=7<77chj_T+!m0?UQxe znea6Wrex@34r!X*MA(&fA#}FqEAdvkEOedBFFr53p9gk6E=Bj;ocPqCretumm+md3 z6SZdtM*u8?mh5tDYkhJaEprIAxw{CU*Km2J?gDKYOh5*|bWL2Dp{YHxx`xdJT^lUVo)hq2G_mi~Qu55Olv02aGP-#-V^8b*>_H`_vO%$Yh zPhx7c2G{Qr;kmF4%DRD`1)v|9x*QW-TN)&bw0s5pDaD?KN3JPfuM+p|xO2TCew-CJ zkztflst>hnb7{*EC>1ny=jo_I3rIo!zxx~@PCAKRiLPrny2;k`LlS=iArGwdil1TrWvX^{DgmGY z-pIc^H7E6?`Zh;Idiiy2m1_*2&yitGmySRUjvN$FX->OK?n{-~cITnCcMrEDJs8@n zbDrt11yzKBqb}dOfjMb5MQem8w^%>Ot?=H9v_LMDWt~DdLmb=dM#9A@5!rfc$;ybZM6kbE;=Q{~t5 zY>lA0;%)Lc#x>DoMkh41L=pltx^AldW&Y8~v`Pad*?)|+IRPoXiN2k<~JZr;fdvoIhfRL2>jB#IZK-ZHUx z$+oY|uooFKTaolZqe>4h^sfScmk)V~M(BIz{|u(%tkJSJvxGD`xIQ7%zu$Z)wpLfi zg2z*Hb06%keL->>Oa(m1@I5B1{BagpFRt^aAY(<8waEm!FRHh#HSuI9P|b%Af*8T77dY}G4-ieaJlN% zr*ofgVB^L2S^CS|4D}DgTl`pKcb*dKKh(?9d&w8dYJ7x%&K6f#d=_Kd@44IcFpX3P zfbI9C>+c;xS`o~2gkO0`W1_E58cp7Eo3KWV0Sy5}9UQM2u8tLkgeo+k1(Mb=G&wor zX2j?z_g?S?b=v$ZaCjK}84aJC zD}LwA)lpD%Lj9PvI@{Ee${ssG?!}1|qv~aPv09t|Nxr|pjH#Xf#5}YdHU2Zs;FdJrk9jpvR^QK~rr~}9ina;`kRr_cm>S`L|%hi|wz~A;h z%*rgCTyteE9^8(zXnlAqHj|6{B>9X}zMFK|A^k=_pN`}&$SO|wL#@lfKbKrT<#P;v z50`0EO?x_-G5(*O-P-SS{x3p*naiEJw1)M&-U^n;?qUlvg1pWaUE{G3kVj104`_h{ zS<*Y#QLq$|%G(eMX-0tYp;iBChu(q=J_so5#G0V%LhW zk8*f=gQ$aea>?bhU0U6|Ur&>G_8~zf)=Rz^d}^qh-OhIa&c)y{EztcyejncXEP7cX zHZ=d>>p-qLwQT1{D)P#rvL1Fm82Yf0swcqGh;11DY{ANf&%DU+0KAc%DI9nRN(8Eo zAQL9edbfWCDp&ng*RJp!5z0OgN^&*foqG!K^+O1r;3`-!h8JyDUSgvg0KW{GViCu! zoM#^`n*#Ty+Wn z*qv;ly-=B|$RmR8>m>0s$+HbN)M7s3tr2HtPo$yQXf1W~e))G72pr75#qsaVruokr zmOO#9`<91W=ciilv|hxTeN)Xjyq#dRN-m2EH>IyN6hc;no*>vI_6qx+3wBH!XS417 zsdq%@+64B}$F4;+9tP==2^7O8Nkt?cl$>9zG9!c89P(t&5%Tz50OtShy*a@h3{zs7 z9ywsXe*REQ0v!N9rkct3qN1+i2=e1DSSHX8NywweKHv2Z8Nr7?$Y+J<@k(C&8D%mc zUIcpB<8yD!_V2FsmyO{djXVn!<(Xft*6LZI<%g7uxLy#q?(T35T!P&z&d=wiJwlW$ zi+C7;@yK{0PkQ?=wGV{D;EcD4-=?oc5k{k{OBV_iTETOzpeo7z>9oHosDCI6)}*e_ zkm~1;%Qd!g>rwnJeTskxm^Z>PWf;@?>!23^9Zcj)%Ko2x+-^i>qt! z4#6Pp4M`y3@GppS--O+9&t4|4;cSLYg#Dn=K%e@Lx_XcH?zXUXtAm?}a!^Z*hpnVNu-8!c+|kdPuh`_=vJ=a6)ccI8{SyTc$!_hsp7A#WF)&y)TI!OhVhX~f zNJ%~J)b*A%7>#6+s0v@0AJ^hEK;xYf@RV>cb;WOs+Koo;<2=B8t!^mgKZAwAD8LeU z$;vM${yb=#AOP;@le+Y(^My?dkX#$)ESwt~;x7I@+-EAxl%4mPDCyL{;b7Amnd=dC>{1+ zo(HeP+;v?l>`=(=GV|BZ?pyebj||%KbKSX4S^bkc+w?XC#=QC?|KjgUx|G7fzpz^{%{RWC_awe99x4*DkDO z@JNy}y1{#tz356E4WutI{smKSmfFWg?Vp(M^8{fL{3cxex1-4m)pUzRt?Wp>uj5G% zcG~IZo?-1E96}&g3CcoyY?q8k-c!JHWM|%yUSzA&Yp>$Pdy-;RTD=MoKen8E&Z_-P z6^9k1R(JsI%ZTC)tNh>9jXo`cxR1}YVaYjKei9~MC{^euf*wT>H5udU_fN0`JBG=_7U=Ejexuv^oj9b>j5oj)XAB8BNMtJ%F6cz>u+`TXGDNZr@=6^t!XWv+ut6y zKF0&PFS2W}EUrn=xhGt6=Ro7E$qA-+w&!j*6`laJw<6LjwL3B^K~iVYZu+6n_MD}e zDBljxD2urvtY07CzbK?SZJunB@!@iVY18R+w(rGJH>~c^yCsUL)!7pqBR~5C3CmK$Y5Agn5T`mT-c$CRI8?`5_eTQucl6}bhKKp$jsY` z|9DmKM5L*~ibK+`5LcfrpVf6!IF(JE98Xun5y?+v^qX0xU0gx@1&rQ2d=Bm$-M4^x^~#UIr6!TLF8d|fewlK1jpyL0Lga%w=1@D?^cYPcs>M(}%oj&e|#hs=swvnKjs zo|PBRb-hsi{6I;#+|oNim9Psaqveu>vq00VQvGOYfZWKr`3JFyH} zR|AK7pXGSC;+vixeP$C5tc9G`C6-Y~x-EkZ%4Rr*Y}BsTEaqk}+p}XIcZV^DxhU_U zn`=VKGHq3)x&g_2oZF-Om}Z$*c;&9{Enc@BXy%`czu&zv-g8g0XAkpL0j-X_ znQ90k?YZ71TKJpZV-BRHZWHw@j<8W$%>1XWS&;-w zYGNs#dt#g4guL4WAMC=fHxUmw3o);Ae&(IuSRHVWFl}W)`HfV2{}& zNLApP?lC{IFL_XEN`%Ut5AKSy#G=}%oqgN#=5n9p*ja7=@gS3t&Q9i2yr*P#eD|_F zX0q@k-!XyKJJYD^QRDEgv>>CQ{a<76q0&f|ySFp7HqP7OM&b;6c>&<( zB9xTmt2Xk!ZVL!pP_BC^ocxUP{1c6KMm#(m`TUL%>)7t@kb!sIv!@x!asr&jW7c5v zndG-$=}$Pi#bV-bxgDDvs4)Y}gM=rI>R)SNE%)ww%HN&mF%)fvPE7> z$A`J@RqG6SKMFFGQP|Tt;?|As^XSCv1+^X~E&@fW6>g7Ifs%6b&eSy*g_=w;0lgbD z6qb~`c)5^({R$xTcjGu_DSs5meIykG$kT|}10X?psEac3bucDdnua6+8*y3T(9*~g0TZC?ft5wc^nr$T7o>bGlh6^ z5oKhkc;V_&h>Oiwl8POJCadC!&{Jti?#sjM7c_9OWCA~J6YUi+?4jjVD45@!lo^`# zHRY?rPId|a$B?qZGe`>H@Z1%_ zBK}wT5ct(g}01 z<|{<2#SghL@7E^LzwJr_#|@yI?=AhXl&j9mcfjg_1T`HZ&7*H^zZNQ&(*U)d9m;_l zUuZHfFKqa|or9yO)cyYEAW;WN1-*Gf!?DnUNz@NG&zECA=KCu)OB>STy%^^se@Ck$ z7GMDR4rvHE<@5?3i3x5m@0-JBLV?Nra*tC(j~)s7e-LhJX8P1ey%IkQ;&qRnFhq76 zW|qkXQl~b zZZ>t}o(*}frgs+9tWIpJ3ZHnBrpU~3Z>QThJhHMbY^5D|!WL1#R|=Z*bb*pMv$Nag z@+_}LMxCy(@J}y!CobAB!D!^zGOl)TYeM4T&AC&W@=tH7e)zRD(=rH}!2Xrv*&I4D ze^T>J;XoU|PSsV4PhVeMh#__~$|kswH<$bgBG@FibXu8n@8N+bWf5?ooCG?;kgTx#IiYeik7XC>gouLGQX>0IfhK@DqYek5D9f}O$KUm{-CL2T>pNcVec zYng2%lX$i-SBH*d+^jyi{~%MB;d=Cv)sY0%t%>5N?60)B>4$`2g$6nPqqyCsWefi^ zm>qOp0KMuN*@q+}LW`WDc%%Kyzq`@`e5uZ|TFVQ;p1y4kr7f$*EiOLYNWoIt2|0IXf9{$|iI(Ao$&-qbmpF*OEA>b-+k7*MIgw9T zvtq^D3`TU<*3bK9+{t+%#&;)c^0RF%N;9OYdV zxWGZN?HkJ?k(Uc6|L@vD@1EuBCJycoaNYl|D}mRui1t_Yn>Fia?B8CBo3~fEn1z|I zo7z67&?s2`Ytcgs0^`T-Uck=y>4(`xAHhh~3Lu^6rIP=4x5#<*4N;6@_QM48q_FIP zch+IMgV~8K#&a!v^JvSe75Pq;lA3QGrCI&J zGf+L00Dl~dRJbuVW?!rQQsZyW(7TBY(+4zF3`#rFGx9O76AJ;iqyJxgn0}JsKI{&2h>NppBrRQd&w_S(r zfBCY2{|w3-dO15z8`=L9dl4m(3(z0CeP4ny~f;u&N*- zO;xWsU3+@f{f3cf2TS!EnwO$6>2%$aN7G{p>-t;es|KOJyrP6g+bTFRkSFw|0yccwT%8A|>`ew&vMck+Jqw9|rP@AuNYkfN`e47?(_UnW}U8`dV!D{YIX8g6<*8$VF zq^1`=n0>KlztmucSH8lrnoDJunj61Lzu@Mcbpbje!2v+O*=}%bU+F(9{fdWdFJ(r= zJWkM$yi3)xO|@|Wn#_?7p{Mmx_L^q*W>;1RA?ygOuXPy-@$?@3p;GHJQFJ9T<-6Rc z6zAfD6F0;vhXpJU<)x99jRA{2rzKV!2W!6XES&+R(Uj4_Etb@VZD)NKGwqD!u@izl z3@tpT2^UcM!H@ckE63=sSHBa!@)&n}6?1Qsf!DlA(L45oHW-)4y$m!4${hW)_y0Wv z+1V15YTa(I?9uB@(4>m2Ezz034mpV3#({F9GaPMG-0)`cD>~Tg9BZ(2jJU3-B0s{J zU8@y?iQ|QVHIi5(8i8|rkuw3F{fC`s2{<2cF%QmsZ20;C|B=>a8LJB+SeBW^n7bu-DKGpUfm3N4n4QZxtY_>UTff@Yp7FHkL;ycRh zV_=oE!BnsiVstTQz0;$MhB)8TU&5h9Kx9{*`Z*UI`7xB7ghDH`n4^_W*@`-wL|@Z2 zPjfRu+E(3IZDy6-O8cIyQ5|}|cH4AwC8VT6`PKKM<0L1oaBo5voaF&;D#Y{KAscYd z)`4jo;teYbnjW$a^>SzPg?!qeZJs<$Afp!jR!&#}*p&=To<9YizfknlKn_;64DDqd7EcrTQPqV)e?BR{8z5gkYuZ{+@ zy%C%|34V?_kD>k%oPR(r#S$(u?+5{;=!SF=Rm0@{@Q853v}z1lqPGMe zR4`PvV)z{K`Q$f|WaS!xKCGkciN9w+6_BNGx_B=af2-X6O6lq4p8nNCI#G&WnmNvK@3Lr`WQZVOZkwT~TF{2b{_5A~4CB-Lc z-NC_{0a<HU*ci*3_%UYh6Tq3*3srv=^*1N$oX_O-Apl;__$ zDx5>sb6#1QG%{moMNti4B1xu3h=gEzdk+}dpeSMyP8y{fv&l+9xZTD3*|(X$(^BOc2nJg~+1 ztDTJs>>|b{0Pgb~jT;O~ty7rPf z;qer*%rwSwNkCJwi_wV3epB1#>4 z>=Eqm=1Mf*eq^Ls<-t1`emjWQtBO4A82d2kf%Sy@nJVs&4kIT(`4-@PNxr~UgS z$FR1R{Crd4v0-tI=v9C2WbgM2`<**hX9jSa?B&$;pyC{;*KI8YXI@Kabx-W(QU2yC zrHr(h?Y~8SRILr{Q74~#m-Eeu@dtARCce_i+zw_moSHh-UDqy*!)TT-r@Nkx4I;iu z#QLYQHt>KiP!vTsjP(g1I{L|Og(D9dT))h%-VoL7lYKjG3-6bUQIV=1~|;Aw0=@+_lIzT@a-+W4o^O794s_1Kl<*V z*@DUPDNUOyj>E<0Aeh`^@yY`xV5gt2VWFBxz4u_ zJX(^wR%q#bgAj9B-$$rf8NIRlW^OWZUG9>;cxO7@L1#;Mbj4#bu0D7AcuXTW6QDj- zkRZiGs&H9b?ZEEb9eMdZA(IA1c3C=}b!7)Tx>|5T7;bLgI?Q1Qas!6W@k>_X&+XNa zll`B;FLMHI&OJ7^hpt;!B`7?qs-1I+_V%~G6H3l$1pE(Ouy=bg z=d`s&L3{b!sR-uqu5^F^WIHYv4910Ml${Q87Ejap7#B0{hpr58rNG4du-5Ukx9(v5SR>8Z zX}z1Sn*0vp_F#9|-wV>!EaFOeaNV0qEHgrIHDVRJ=13-yab=Q1<(^?2 zVVJ?3PyhGl8TBUU2H~GAOe7K z&}Y&&1rH^YxoG#;Vml{r*V-!?RoW`FF__qNoji&=zidicHf$*RW^kF*FmY}c*eS|- zd0Fvvb2$?%UfOD<^`+|J(Gw@n?Pu-;>&#Ko`p*W_soG*>`GUe9ipyOSwx=8{t-T*D zf`&N`*bA3-L#dFs+HYoNzFd2X`E!@m(mY7QcNqKh4@e*|bbOG^0AnIwFmmQZTnrW% z4>6xu`jS7c|Cdu*VtRRjA5oaA2FIxL4!z&B)9^hPXdfYkeldU%!OoUB;`M3FOlGu~ zj`SjD48+qY=fLeoXR>U>aEywKe1?7#p@f0eZE zz+ZEqlOIS+wf=C}uu&lStZ8&>`&guDUIXuunD~Cs>8?_-y9uy-e&4t9NMg}pF0j<# zXWNcQn;93MhQiy3f5_2P&*T*wYc7naLB4HUT3JGe5J_r}?ig_0r~@0;igQh`(4CAW zQwXJ3>1!rBW64Y?fNlBwqzQl7d@7`ur`*CRTFVr^593zO`A6M4u&m>e>D6DjR(^K) zCmYqwD$iQ8#npzfA3V+0Tbww==%MK-9_kDNp*YAvm2j@A>5et5=U%_RVzLpO%#j8~ zPd5O;i~*H=#q0F99Gtf1(K?9>9O#LYvOJb<#R8S9mW`?{2de+Lo)*Sr5KE?*k$KcM z|Gx4-w2qt4?8R&Q$Jg6(#qU67g&2*MU`*lLTU!6W)+L5pX=S?Yosq$J&YLD3OWIs8 z%hO>uc>@rfwr9lQx^~*_a7mqmYgnQ%d7ryEr=MtYrW-vCwdK^^umKhwTEGqTxO8BN zX+T;>j*9@wYi!%t-Md`a=kL0i_?WZvgxY8Y&|1xiVe@8bE%RAoJ<9vM9RL_Jw)vO>@j8|2r-|Y$Nuvt9rYQ`MyZ! zHM>u3^5qyPkCcSF(K~L<4LubX!F6*|09FGih(Zdg*Y9{l1s!yn%-99`5nA_{)XNQ& z(_A=Mx7z9*_j~?CGBv5ivk1SB4=7xOY=DgYhKo)-1=I)O**wFb9n$;e(0mM9OA5d{@Y?UOAH!FM za*V+yoiz;-X|bk6fO=V%?7$W5+&7`~u7T}$uUY|^XcD1o5M!YI+7BA$f}+%<*vCSS zR~Y>(t!%4?Vi;k@!yoMburQhxI+%B|qt~yCZ&j9Y*?XcgY3ncd7Rcf}`;41bY)#sz z9$19WYj6#k;C|3X_iwR;^QHB)a~@A7O?59R2Z;PSBLC%A;JF6a`~=p6hYUFv`qcNu zZCG(B!Z4^rXY4+N3*gCbVm{r&(x|o$y?j%raQj`%e=s-xsLfVm<73yp__ci#cm&2S zNyYKaFXpe0)&ev6ZzNY)s&ljKoU0&mf!ozQ&^qCa|Ky!p{#P~rW}pG6stzP22lR@& z;+|C4PM5`Kb0okkiivZ^<|Z3r8i%Zl+o4Dp)c%$lPxI?ZF&mmXgR`L62vQau;PIUPWjazQOFgZRD2N1x{b3 zS)h1|wk?Wd%Tvr8$}83$T74l_$9LM?u4gnQ?Ld~kS-n@d*7}!U3Xa5@hPW$rvitma zi#D#;@?SlF3ekXa-|9?_JKqR1+gQWn9C(H4GM*kS088vek)CaM?*51tTgy)!VLY}Q zA4q#m)2zO{4Pj*#(V4!;C`c5y*Gr%IZgqZ5*fJ zk9R~mX!ngHm(~rAuXryyc7#)dsFE`?@pjmxPp+#ifiM6MfQt~rAFhWF70a}rYf}_|^wLy_LPP_f zNVvEkpdruIydS^>afCMx9%|TFRC%ekkWMs%1)-SWsA{8cdQ$K*U<~zb(WN8m z)8LWR&=^!c_Qmp)@@d{HTW$9I@ipE^<(M8)o^VRkTr3CLh3Sh6c$p5`Ahv*L&{OV5 zn&qn&LkXKGE`kJz`yF76qQ!!PxtM7knzEQyzJ%SW7x*>M2x?S*dO5Ers0CcxIySfq#}vIl@}JI8zlfwws;oeC>(aU?ksgWNv5W z0iyHjkLvdj!#SK6|)7H}w1>f=ZT-wYTo~-J|?>lp)Lu^{GB{V7ND=>x9R+Xz_un z@@;drUyjU<^lF&xHolMj5fYtjfP{hljA?S0A7@q1iT#P5@a4;L3{+ zssU<*mIGx`8%4$;8>grXh<_m$ms8|Vx8fincG&b`9VNNKM)NxR{T+2j9#g6k+!O4q zvwiMWwmY`>JRUQH+cY{RW%=}|zz&z&FF0Nh@VNY&wwJrd^=~%B7}QC5fySp z!(nU>j*nY~RFMQal}=E~>s+2Nq2Hw9n#TmP;=rh^V&5EaCAPnj%5N-KdTg2nQ8wR- zQ_Hc;H2tjg6f=0cPu$62IEDgQ?FXF>hu!+J6Sg2Rw=d$oyTbIl= zxqZ+kPMyWK#ebumU69qmsg(XaHH@*%Q}yh2kotH34|=AYewvhwDq<$^XS%fK16={M z1nj-32;Ki{K>GZrlhtJ0cy9X6D!Y$U>YA?c>GysN1P7@f?2c@#f5haZd}OoI)`Hk8 zLgcX9{Maq58v6Tb4t6AU7X}&z#cqFf7=m~tZ{6x2bTUzD7DUn1SB3LkEQ{&ddkgK zV&prcT(@yteFr6_MK^#I4V9AmOVLOQeA)Nrt+n5G;bjL)YB{f{pI(vdro`6 ze+c}k{jK4?V8Qamu`}xbc~QDRwfm{)&49YwL_Hz`(f0LbWkae_Z_$y8)zv0shi*ZO z-rVRP53v{08Je`h4>;9(J0A!ZL$eySe0DC-h4FuO+5Y#sAfPG@-6(5qFqB|UbhB)z zXiKOC8s4~-qX~HY5WBABeZg*N$Zk>J9X*H2g9UG$(z@G=fWX zz%n~~c&dFSoNk)f4vrAz$-^s-=-w+?EmDs_F8v7k+tsT-AuWurd=3~I%&=_LM(*WY zVOJ&YW)R3%b}aI1*YdKtGKYWbwaZcVSlhjW9hVkmJ^2KC0?}Y{znEd3aiW>y=ETZ> zZbHMnb3$8QeT|>N?BGSw-2-x&U#x!c>8tr&GH+dZRVo9CZ7{L4nFe})#M@4JrS~n+ zt2PIiSWcQjsVUjBp*-VYxYvr7iwyo>X`NM0LF1E@el(TJ~j5rm7@0I*5^13wO$FAU(fFggfuUBKO%A68r10iuq&@Sw$+)Ge5^{{92Oe4U-Tm*Sdl z4GLS0{#CciY*N&1z?dF^Vs1YixXs196AvaK9f&n}XyD<=;J&UuZ%IUq$pUALD*8 znkkHSvw7`liS4N$yKJeyfA@HI>a3XeR(>gxLu!S(Muts%Rq`bhl3Hydl*)+#QRK?M znG4xtSMf5H&dY=SLNn`gJK|}O)R;5wJ@eW&OKhv2@up?(jT)c1zv}3lVsdQ_`yAd3 z=LM1Ow03%GN%NjXg~%!a&b3Co*rm61Cgl$TgvoVFvvhNodk;6^1I~vxja3Z>33+_j!~g#JJMSLg1r<(i zJm$22q#v)){7GDcRh$YOmL6iL2)+VAk3*G`D=s`nUMf?+qE+Cf0-z(WL8g66_DTJD z%Nxe7ZZoO>SQJyFJQi}n>4K=NQQA<-QNInj+}-!kD<*BiXXlq`%dT$z@Zr$!1$L2t z&J}mQdgqgBeN*&ms4VC#n_+cs)x}M5e#S|wg`;8kvJjK8S$!T(J$v%iFZ^GAs&ti2 zpZk;hm{xiStN3KA+pZ~Z1!)^EWr*$i&6aq)GFR0e>MnS}jQ_Empxv(@D-T^^ojfyi z_h@&@$Tt61@rI@6gCAZNYE^Ei`R&fxSCyOV9o3xpiIpDKxyQ`)*BY73T&r7QvrrLS zwF+|Ey!)2%the2#?Mfz~lv-PV*t3yYJeglt{2G}#?NfxAW7wM;SaM&{wp3P=Tay1( zc8DLCKeMMbNpvmrSgTQ{T8;^Ww$-Ha@(W|Z`uReOpYMG*zK`{5jcBFc)D$!8>j`0 zL|xv{EMX9EQy6{^h^NevlbpwO%M5aYN5hDF>zBEW@;EDYZ@+x~$qyT~M^P@7BxmK! zqA;r*ok8wX>}pvfJ0UC-(pdUezIS`i3y{wYm*Tko%riQ0S6-I?+V%Z$p)5QIX`0`&vt+((>R#T#snX8Yzn`e&zZRB)5#aBjJM3|r zs#5{H#zR$6^LE#S4=#_=6P6}_{XAtv{5#S4wWlrQt=ySV%a2vsj~S%3YR_8HVcbjZ zAUSDHOl=MK5~u{p|I5ud_!A201MMN0;JleH2ferWN~{z1lsciVjPxgSJ@JtZA~kRq zU^rvy=C2+EhWPOmW7W&qfqvYw{8BCse+za9`P)nPmro~o>`gcx$h|Z_wf<~_&-qW)DR7r0*`{OL1{Lz0hZ6sfmS&4qIusdZKp7N|T^Xxyx zeotJuK<>6*^65VzZ7O#wOdeHQRagSP`*AlN4*7Y5+I{XTC9jUajc=h(r696I+>W(oJJHF*FVXAuL$QA1y^$+67MqqH|D^%up`d6&Iwop|} z_+6gPJos>ZJ6}yWIj`8)ey{R0?dit}m(N-+z8G~7Lam}_Cj~CIXJPNb)=8oeIN4Zx z!}*eIoX%3UYzH@WR=p=@K)m|YyzM*%@irzi%liE$N3*?W|1z%cv6xG9A9aYXKKaH) zq{uksAW{`(dOrx`{!tlL;z@LlIs4Si`>eGvDtLVv`|D+^-(75;skpXqY2u?mW<%MC z^NILvX|#XwB6GTA`^7T7kpY`BHPo?c+WC~e#c#mFeTsF0{+WEeh{McsL9Dwp;8fwm z@^X<~ocZGQ_vRKBZmGa~;@o6zcXQHbE*aY`C?1T{AKfSXsV0V(M6|rD-LjICPhWRI zKi^~O?(ob_xhLAz>?Iz2rw$TZzCC3ZwOg2Rk^gn)k`3FqR}B|z5DYq)sqEg&)r)XQSS>TPcHoowHwm zgZQq8%kP&q6sH6jPWfnjnK2|7y>@goSEe7;+ax12@>r1Sf!hbZ)tqs8v@-1ii1wlE z-b=CUr<7!-WnntmAf`K3nSa+2 zbKX+r!WjsW`I(ro7I>%r3w8MvR}&&v2>ffG*VUWaylLm0Fq94^PiSFlpO;!lh$Mzf zChcpY4J5~bKJ6WB`qrQXP*a2|X4ETYm$`zfL&iE?!`@j3;Wkhl(XXj+7W7111wjvZ z8zI(L)oN`MxK9{tR}JtWr6S&+XlYwIA_jBayB3D*9V23?YrbLF6xCyys^D4gaCGN_ zwFi3K=99mIDvo0flKz$PIlJf?hYapJS{5V_H+3={g^8rRU=Kg}em}lLkC*?+#8C+%b0c68w3S)>-W7c zvc=Lwq=err+Te_T`7I8kcwOd=;G%s= z)qbsRzg2jx(VFFZDj*Pwc{_x?U#sn<|GU$WJ@cwNNIK%0tY}Lxc*XBInN;G$RK5gx znHy4TcNTlYMaSJpHzu{f5CWDJq{TkpeO>yk>iCR;NG^`Va!e$(4t+}jMjLLqh(*ub zE27LYlyrky)KcRzVuW2NyYEksW81L7dgU$U1lcKM4JQwTu+k^)Px#Eq-9F0wqF}6b zwwbylJ69$c^k9E&+nsTd!EW2K2XFaF{anUrD@kS%ZFq}yG;K&UOsuuuBN8{y+!*S{ z=Y2D@EYi6aGf)1FQ()I!Y1SZp${+F>=Il|X)2{HvP?zJ4x4bR?#yoqTirg)%X=Dv| ztP(UG?mdy{l5x2IM6IWKONV8{VAoEb(WR-5A4|W z#tMTw71-6++^0j5buS?!NF{25UDTmc^6?Lw@7Capm;)T>(#cZ@V{58#_{>qhGQRVX zp#UEcsK{Yi$p3>#L&N(t8St9{+di8imlBQ`Stc9jSutQbz(1Va74?7$ zAvRN^v5wBzzcbyG&s}3DO`Tv-8hx>McclTLkrO)NH~pp2u!wWZxti0iX*86=Gd;*h zrVnGgc6`?QA!hOoj|ZOBW!5HW!6PEgZz0vu4Lz#lW z)o=Oo3nLDSQ0%MZoPI8Iv>+sIcTonoz55jLk0FJBkQe1JB2eCQUp)N7ngvYGp6HHj zlMGB-vYUNN^^5sjm}mP1UYxX`N|uv-PZgMi%~izI$dg8ro;lGS7Cdu&>2ghKl2xxd zef-MqsFol_&LwFtWs;R&dBZhnX!2&&n$8u2vkl#tY;~u)bV*3uvgjl0SxDU8~jd zL;?0y<^+4&_VatiJd4%KU!|To{_>9$E)ce*)6EpMH=<{iGw9raB|MB-C7ov+3xbiGnGtT^MQgH8zmnNSg={b%%oAo3An0P4UJ2Z7pEF5>2EzrsxP-Bxs5%Nbc zGzOfSH9HIcN_xR+1NaIqooN9mIH3eSwmEg%(^gbK@oMVU{wtuifo}ygRxR4d(#8RG z4f%j78R|@b?+-!BkfQ>rG^dJtY;~6WU_EOtL%N7aL>G+eEHaJwnBuWS9W~!1hS_On zUppids5*P6%j0S$TOqkT7Y;fsmXml`)s9aTdQa?vS$^_QBDDSY-)iv$9Ow-I7gs z3AM_UutI|gj1S~cG;)qycUy-&k-eF(J`C0BARoOd!=YsJt<;Sb2F8kuZxVC2oZ>6j z?{_ig3!NXVcwrppymj-mo57ZWmdQ1*^-P}`yx%>-@VlI#yydjY)0l1VpWm(S^NF`A z;cbmN)2$brx@HEq{Ks!wLtXtHr)BD8l+?bazZDp-zZE}!7np4E1V92-#qOd|*+bJn z(>&WMLmflNP{hVi+s!25!?otN?U^zcignO?e!T%3#! zFzCdJ1I;O((X)3~wr)G~CvE?Y9f{)L4rmsXBFx<48M8gb({*S>NV>A&^ox5I`8+zl zO2ured^`Tvp~qU8 zUDX5Z9|;IcHr0*ll|M4k?qx_px@>dk=`OL@Bl+&0Hk^e(^=6c4Z=a}9Um1fZ;A6;r zn&k96aQ*WCt**B6u|H(IB&!Gy~1+Wk)Dt)j1LXF36I5xfku_?5*@q5`feIgo-{%}O$j(m zcMc4u!n9Z$V()+0;6#3hT>m-cQFg>#PPR-Bej~U6gOB`XA6miLas0ljk){~>f5NZ~ zzX2$}%$9u_8bVwOn6w0W&`>Bkl8}n085wy-kl%VX>KBw-4pp<`g7r6c-D93SW*eK@ zdobQQbC=iUGljhn3dns#{$@nZ)azBm|9v=mtI46N3&!NJNFTp%$^$Rg4C86px##^o zYpkE%9UnD4rN64AvRalVYg?-BQip6yU$iZOZ}9QT@~WNJ>slT{D;Z(pD4wfOZ}T*J zT^CfhMA=bo*b!k|i@BtAD9(qFk1Wdb^z%NN9cZgNwDf92D^FB8BA16fcPQ3jyVN@4 zIm4)PpxiG}R~YA6G~jFa$ZP%HXk{(&Z`GwTP!vZVB=}0sa@BXpE#AxZja{GUtvy3F zr*oga#cE}6sEpJ4mpq1!pM7x1lQwmF;eF)%mTlnux?!@PYlvbnx(87+u)w)6Or5C0 zT0jcVYWn+tC<D>Q2eikA|fwT*^TFR!n0|eCC~)K&~y(3QJ99(5D6XUq;3p* z3fci)3U-(fQ9_zM^R=VD|7uI*S`L6)8*XN{WNyV=S*#>%5bvmpV0OE`cCv~guaO3`@~qp&UF^k=QVWHx_sB$gL+o!8I2 z$+Om48B>F8Y$6I?LeW!~GWq?dI0{mEF1<*UoLnMlgG2niwClkhbfwCw6wTJbOaeQF5D@zUzab?zNkBHd^0i z7BjzU*f7*rv@S{KR)1c_2SIsOj*ESTENU#T!w7 zhoul*+sRR%1R90h>JHqI>q1YS<~H)MXF^Bz+`H;A>rgnIrXaISuRkU(7}LgX;H$=< zhloP^0O$sqQV&6iaw2cd|J+&J9&BLx>maOSra;gz+Npn&p-~6ewRJnv?mudJ7jqPm z5)_Vh#2sh=3`Kn|reTY(M?hEXjx5uo{NzCEE4v5yyA=B(vK%V>b)E#Q-@y}Itv?%A zyt@Nho7l;)j7+EIIK}scMUNV{D1#@?Wd9KGmNi^fJab0PZ}_QE&N+FX+uh8eC`IwI z(qwtqPr7Rz7wF@c5A8~Fe|n=N@XjXU43}N!&BF8S4xB#!8xq=4E1^2 zj&ae2kAE7FRs;w_BDEZA{j8PT7hS#i*30@ct?o5F{U2daUPW@uqv!055u_|tC?c>y zSGgfQS{?1Ay8FsR-^6Fgc+)DMT?>|8Yzvk?6;(+pMtl^0x9cwRom5XTW2tS=n}tb(GDY9ph=>m*!+t&)%xYn~-? zNA9ZyskO)VwWq_~@WfixY5c7>b`T5f7I9F$nZ#H1JZocyxO$qw;wvfMy@$e_fMc<< zY&nIFe5>boYRsNxHTi0NMGtcm^^(c*Y%8J9QfTc}LA$AQmc*cv>NXSB9lny@$ah<3C$5=Z7h@ZoTRqyTz`8#0l^Y8`h$u~33=UTK|zW#D7yZ#Zh zD>lAmdfCTi%P14;ieKPJW)gQ@_6SmnGJ+l6#~WTBDA|Yg?FDD-K8K!_e;3j^Qx59L zbJacko4jQEr;CsOwfSLORriq`;be&7DRuFMrHo= z`&r}93Y0q&cx<&4!QIB(r< zO<3}~Qex(mew_OrlUdLtl0A9D{dQidx@Q-cuXlQ#z!l3o)3$j=TirC*+w}7?1H0?_ zzI5m>KD&dLA~ezKv3vT67#=*a6b?N+Vo;dsw=yO!kZ#>w;2r^(04#UKKF5H~iMruI z3u*@%GC>Y%!*fg>PgH8TUUO@qK~SHrIn0tNqxE$sTdShFXrrBVP*9iU4H;s$>wk$e z;-#H-{Kbp7tPKk(%#v@G0A@Ekt~})BzcwI}ef4&(${ZSI_IZA_sC!9p%Ee^J@#M|i z7I%DkV0Nz3 zO-z(*a*b8}f|v4vqeJPG%=c3l!#?tXh0rEarsZpUUZCSEPWu?~O+RaGQgQz&fi~h) zmu6V5XTpX{sCL%lqn5Jvk)sCR3zPepY4;Z=FALLAGLe%`^lv6+6T)m62)wEnob+>+zh34%>1N

H*|H-er(1yQ|NucL><|gFni5hu9>RMy>Lk@-3bKCj%#oTW`4}Ipw(Av~d2S z`AbdfmXEi#21`&u)mN{_3RYUVv?@6#V=VctOEybfaC_VSl~ueIZb#OcSm>X*m^^-= z8riVYMgY#m%%=ePsn6z^K$kT_)N)! z|12wgBbYOhSOtKFY+G{2(M`RW6K5jASBg|LxSboea^JL?P|%Ui!y4R0q)NIdaGZA* zgO^lX&eMO8YiJ7k5pW!MsJPnh>_@YoWc!Y*=gd*zXgF7bWSIj znN51)-y2nw7XLA3ejbF4u9}GZQCs|k75n^`sz@*t;%UO7#i5Z<(RsnpGV#$@u3$tu zuw9vVeuwBFmceQuA+#F%L>nr0w!4B|-3*AR1G_bGM_p&)S6OCjDCu(trv54BPvPNOP zgjTi=cA9s*4fx3id-e1vHCFTtfVu8}4JU#|`kj#a0YmLzzZwB7jJ=NY%VPn@HnA-4 zl{Hk~)&VR)(GNV!R7W!hWw<(9QB0XRd|^Kq-GAqDYOw^Okg0;id`ZmYQ^!e&*iRYRDt^|Wodly%Ai`=+~eFAfM~$SMLW{53Go|Izj2+Hc)gAXa~B!_+r6lt*?C>xl|27(MZD7<%uIcXbR+% z9%g+(y$YgnQ54ZP(CHo)3Z0Ulv*D?XANZ|Eny`g0D`rhBWQy?NuYusP&8I~g;4+Td4q9k*N-xy~zV^t z9BAmB^#i`mG4v8&J~+_f0aE^6Gpr9e+1l{us^jyn^;8)=nGF;JRsv7=Nc)?Yo|BL= zgZ7xk6g?o?O^G~S)ZFezKja;kJUC1K8w*N^Y@gttGP)hZD$FW?*%*VK>YcjYytQ;z z*oIgx-U$vMXsvj2x$#=9a>me)q&-w*ffDTB8JMzsDxp>~o>c~MxG*;$X5%(!a{(X+ zVQV2QXd!jt3WPLhNO`F9A{ttP*ilE6SY8HqUP!yiHJ$9s6PvjNsz$GekYw~ob=PBz zIyaqYbs+Uc2jXhbgf$u_4tR)?XPD>;7~z=a*%Qg=5(r5>1eQUn#uf44KVT{sixTf$ zG<3U9Keyf>C3k2JM7F@a^;NH{R|E@G*svKoyC5pm32(Qd7eS@LU{&RDrod3@PcPMh z&;<;ll+RzDOGe!@a2Yggg%j!vgB*@P>;kx5e*Yzj{rAb|&JKLa>pV zo-p=^Hwd5pXCh2j2DEBJSpMos;0=~9nH#r-{SlrO#jH*HAXPg^mbN%MBlyAwf-vO1 zfSns(1?M_K9;P_c(v53ProX>{eIlA9WPRG2I8v_~@4QQtFqGXGhV6@F_f8`|R5O9n zm`BVu8!uV8Q74nS$8xn;HU8lMiB!CSd#>`~hHHi~2itq`(S- z$jqm(wQbr&I;@H^lRZbr9}ZC0{N(?M;EAXOZ~3xBXqb#nX>jLKFwjh59GSN!7ZOs? zL?t|rZ`OezQU-VYZEirVWP~izkeqIEGzK9yPgxZ=Me~7o;{+5F*k!|)QTuxS^B-L! z=7+JM{&O~10pyme78zyQV5c38g?Oh$0#W*ir}(6BiZxpQRRn)0ocQaMYu%g>YuJp#EN5G3*T6vSAMUe)hee)96~({l`3 zX2?{<5I*!k*2cAjw1|k$S`bLOuNB|kFp_?&{|0e;Ui+s&8l0T@i60l26FZla4Tlao zFYqR5SdS=C9mE|^*?4DlvfN#T;5T}sm@sdgGU&0&e!HC@)7d#F=MR~0OQ~)}*zRcw zGg~d_Wu z5dtTQpn&Hc4}bui!lb++(h=k^IVoqYHR@lvQ82Q-#o5=xFjvwv78rKh^^b(q*37V@ ze4tqEPlsV;XoUX-z{gZpO%^B^>3v5*;{)oQo)0pKc3o{1a1=glm&@N9rQi#aCX6eN zZ#4-3Up@@si*-I={(wGpg1?}+J;M8!siqWN0th?yu;VQJhqORABxW3yG6rl%vAe15 zC-M4rF%r^5%JG2toB|V1WPOHGx z{ERC9c)|+{L*gTRI+fg4s3%2@)AH!VY?uKW;;*O$qDX=9$*u{jrE7gmx(X1S)WBIr zZK%_s&Jkje;8AFBZ)zAi9Pvs&rb-(@fI3b*h0qYOvDPT3N$O98dz+tgP-!4J(q9|Z zHijYYj@xD;QOCMNr5|&2FXJP%zyT=d@`^*|LJ%8H0P`?n0Z=s4;B=g>qc6|iLb3ytJ%NcF1d#>)gSY`APjfJk zq~iA@wUa#_-w9=u2M8OqXZ;kb;cMiS0TTmCWRd4pBM&B=BS-|XbIDYmRTfVJ6t5sn^UrNY)h*a8WIdf;quP=@&)Vw25%_SI$P5`XBUE`^Kf00Uu4}Io7#2FgiZ$yIld3cvPmfGbp1!rPL zo@tqsW1dW(D>4-v)>iG#^gYsHvi-+iDOQNlUJs^zy1IUiJH(i_5O=0CJH`ZRpE(;Z z%+u|Bd0so*mW{tvXK~yPOl7r&o>gNh3H|zcmHRAT5+#7##d{_57WWpZWF9g-J0OIk z4cGg1|B`T$V`$Ht zUE!1LE9SenDMD%;eWWVRL!MU^?_xcm7QD5*^QUpWXi)5ou>1q@oV9aGU(pQ7XDvRHs;D~M5W7nJiJgpruMPm@z?{On`j*$-n++5X(&5yh?APGn zIZX*zAgNd=UJNL1cf2(E*X5BtBnwrrySkm@&V2T zC5AM2#Lk-5G@lND2`o+a6X%zR1)%|aITwC+-q*Nr7Pzt?)sK$1C)}w(U*dH&BVVc7 zQqMfxWC_ef)4$RuC)S9a12nB2pjx!%!g1RIrZ$p2M5NpsE2CPWLD|NeFUN^!&N$~a zkb3-sPr{<0!q!rf^Wn3W9<}LvEl0ySvMkO7tc^?O-ZhCMjHM610C5QQ5zGq-ZENYA zsL1C9ik`e|g5*)R@!aj~+coB@S0y4qy-+}a&}Tl|{5%cYr#j8J*{+-gi@=@SS7USz zMRLERXU<|GbcQkX6wn+A916uBnj@$Fr6oCZ7I_h9rI2RVOG9ZmpaUIA=A-?DrXB?K zBpf9uQez^NOGPSwVPOFJGa9VmmAl=B=y6$Ahhu&S{Ta?~egt3>8a#9WFyu_?DSR=P z`u~5O(FiWZg4ME%)C7RX6jikMj~QMM)Vz&1Z|3mH?r$E4gaFlX1J2cFdb`rzmE4D- z8`>A!*%pY2Tp86R?hwx++EC+7lKDJ=4#wF^8Z3U?B;<$}J)Rk#TlR$e0=iu(tnwae zAtQEiV!WqvA@BTpzi))k?6=qo=#D6pEfi%hhkNzifZ|3lTLADaSASqkuHK{zzJrd0 z5aZ;l$ymDKIk{6Zy;O()FzDatpPVYL(>IdbVL0tQvfguh8{YT@bgU#eCN4c7B+UL>ShJ=q~9t`yv#M0d+ zp1<5>%r2W$P=n}~7@atb; zaH1SV?X~(ye?$c|KPuVn0!!Fz7!lcM7EwML%|ZYLA<%IOlL^=vK5Q=g^9L>6DN_xm z;8W7z9NHJNQMYxZPXi2%Wq$%B%|%ZTcBTP#P^{;x@Q)@6|difg%TzGyOVgoAz|sOJ)*`lDlP4Ejc}jt^6J2#k<23J7Fz z+8sRz1A=~9BQk`dC;eM9neV}q-@-KS=y&#>^T7(LKx%;fZ^e;@v|G7wBaA8PWjPG= zQswipv<*PC{%@OSboZ8^O9r^DN=TW8OUArMc);P0!lddsyjN)zwTiD*r`JHO3OKE7 znNdBTgHsQMZtfgm=9SYm(o2Y;q|5$vVxVlNM51JN35T*NpxCIGO(&b%bal z^EC6}MTXc;lYv!1G2|3rp+RNh&*zpvM3B)3tFQFVrz9R=yh%*zy;#RsDx-A;HJ`@7 zc0dg{9_*7o7bd6!Pu?$8hChUZrZVWrlJv)PcvhPm?A`~W;`@fDfWx3rX?9@uCUyce z7G|_~+rTcKB}buVE|7D$-r?=Hnv1yOGl!g>a&whhlfnxWh6{wJm+xx$q5`ZbP5mhg7s;1UR}i92ToeNJCD;3tYxjr|W~{+&utCB$--wTDvCrl9fK8$BJyxNS|%d8X#eL6dD+NPu9p z{I@_@W+>0xDjjVOjHVxHz%=2UyX9j$qZV&QM~SvK@?k{MF4!T8l+rIjarb}W{72l@ z+R{@Xp<1PR+{kEwi0}r%OEsK#O=#hc5?(A&SjHh7?yl8sK2StwXqr3@u4XwE9g zVJpxGQg&h{qSm<}S_`KakE*Ucpr<-P3_D(n_)goNENhm4EYxf%DO=^uy7{2|C^%J+ zNe3Pj+yPDtyiu1eoU}sn+`nt(!-+GU20-_hBi+3C{S3B9|_SVvB5KC6_ zvL1q{4BLyQu*t&TG*RdWz9$JO-mPIzikfWw6SUnQ6+s*@Hb=Omej{VZ!@cX*g6|3{ z=it}bvMlIFp^?3RQ@__%$AJG3O#&OVL;UV*csk0*FSB{cjA@cBrJOM@$zB}wY7^j5 zQ16;zhuvvqwIQ>abCO&<2^2a4-q+27Y|;{{!%$+7p-jaE9SlK&+k~)4pPPu(P!z7) zoS9}3DgdcD!-x&3_XHQd%f4G?_KLUy+wp-t9veB#Q?w(n7(87`P?o5=dI-(}DH$$k zZi0Q#SV@1|1wFt<mcj)d1@Z=D)jlTR_?mCn(H9(5L=WYbF@a1Y5k2R` zY6#CL*=Kz3;`|tejDv3Zq2jkaCjD;=FpQjT)iL5hF%1Kmq z4H*EJ1G0>BL}55}b0-}4B&-42D2ZXy#|KV!uS%eGlP_QawSt$9Ax4_F2v6?G?gDWZ za-b3V6gkOM6&oXYbDdz*y3A~l+9y!y^58=>I(;Q}jN>*=%g1XX4_yrk%izGK!kZkZ ze?3j@TsT02UBH=R;ZcPu3_((_a-x|dRGJVkaYUW7tBE{#^TU@h;4txk5>g-@mK?0a^T<+i zi1Rn9hERbU1{ZAR%&8QiiN9c3@YHFP2@TrdC^I>yxb2M_P*E&ORk3HKanSsS4u@H9 zz96@B9s1n`Z%+;W4V zK&;5~zyMEqG zy}26kggue2Zf~H$jzdFnH^v(h9))ZQ&GDSuI)HBv7;fhf-J`xMyHWPttZ?oDydAz7 zXv6>H*`8wdV8in@Bo)@!a4HW;YG@3o;$Vh=$(oHg(uH1lzaio=arPg*+(}9fh7-5S zOdVJ>Du^?2^B*qIET|?<6bB?tQ=Evuq^*(m+P>1aHFbx}W;-CogyOQQ+bg(cMtyP+ zCScE$#?P-DTuRj~1!KukbQmy3mak*;sZST|f^8^Q2V5-mJh(4oMM=?BccmWQs@QHLh zCXV}_pwjW3!|YVcCiz?pKbRt}7MvDPC z-2QJ8n@|4F!6W7Hys`H`f*GK@mqiZ-xS%eD4_`HqLu7cA1SOrGM6fM7Z&xG|)WJJb3ft%%D91%b- z0Y^wQh81S6NRvuXHK?XAkZF(rpi%cdOqb*Dalka{2#+dY|6+({?yV}+YG60D_ryl1 z6*)jb&6wa#HHliY;s91UQh&(vr#1u8B0H|McW+;K|?`5RF?hj1c!xG``m4wUhSScCqOIUm!+GE`*(_8Hu$-XrHe zYeiAu(X2XlRNMs05$Xxt%sOZL=n%JTa@N0Dg)LSU-~tNLAMh^RPMeymCUL4MpFyu* zO}Vd%qRi?eDlZfhjimDtGEkZGgV({MP-CNqOwW#s+c@=^4Ul~?(HJ!|vp*MZ>4{GR zn&aJyh$D(<`ylAe+wfUyCU?@{0>w1@Z4bV{qxmv7gs%$ms|%-0J^8>?(fr4xWf8N9 zvMGS5qg}G*npzvRA9}N(NttWP5JLm`Crk_*Sw~|({2dN*z)mI`R5?AHQ?Yi3VaAlH za8@;-#$f4bH+YXPCW^!G>tmy11r_*IEB_WP*B! z+_ulhc!~!1iw|tEiy=$c1@mWQ!YW{F+jeiSTPt}Sea4$o!`>`nz*$#kT(;}so7yIh zzY60Hx8t9Px-gpCd8`@IL~fB1>mzQa6Kl(lHRVz+e;VUb_f*TvQ+?0MDYbrlni8f= zJsxl5#m(Hng;ab{6+&;49?GA;2=cb2X-tX$JawxNWFN~a(|tz%|U2J(df&Nq$5DC@nXov)CJ67Sccv&QF z21g7$^a$@`^f==`%cA}RdIUh0uUHlmtUWj7t}&{VcQ9tq#TTB~4(PTK{4La&Bb>SJ z7l)60#qidz;zH#bco8)S?!YSmt@TWUwnj1FQ7BTvcLzg6701q2cFU*gV(D+DQqr?F z>5DD~+c2%SVODqc-xZeVGQb5%SP=%at2}-uEZY{j9MCXOU#I>LR32aMnQ1Wjt!!4f zAk_d}t_^%_oMnRQ+OE)nH-li=hOe-sW}!g#8S#&u8UIv?RKpx3$HBfd+pR0&A_u^T zNQGx^3_*yBM)+kTN^wVE30B19101U2573O_N~Mm5FLq344*ow4BWftLmAzNU>nHl67uAwE))fZRwEYQd-sE zIZe$);zK+1YPMb8n|f^eMah~(b+@E-jV z3#fV&@Tf1J@?XAIZFkc5w;VMPsSh(veqF(V(lQKXuDTke`{Hvf2NK`~WWHdr=fM$( zv_Y^F?;AVb<9hHkrwH#*ab1j6UWH0yl}CvmrB!QUY{)(xAi)$QjU|e+R6EI1>`U4> zO;JWEC2w%ODLsZj;(_acs(=^yomH)(>e9p39jWQ+EQ&m;0?wn^*8@zG_+@sha$oy_ zBs+{HTXWP^U`|DI$-S+=;FpqPjTV{jqM-P-wAHqG2H0}o ztlDg{c|Ui5V2dA?nt}(NHZi~v911j!cm?huVCE81B`^N}RJ{va%-R1x9$94<$+gG~ zLM&U#E=4u0%dlE$*~Ld1iDj3Sa_O=)?_5?cX^@rMHcM8!Yf0E8(v)ZDx&xu|VAHyysvTB^0%IqNM}J$S~YZMr9EN8aHYW%M~3X?q;?x^jY2r|ci) zHhSI_Z@oFN)kS&=Hhx%>)mw^b3HP>@nPXEki*&{oL%;MJ<5 z2M54+ru*pY>!j05bibj_uflMK_2S?1OJB#+1FpZdFT{H14;-^)I$=((m4pS0K6<_@ zeVg%Hzv>su*yFTjrNr#Un%7d*+1LH${Xcmf(x!Y~Va!)F-yu&rI@&d{5Kqq03vi^VKc++cTLv!{ayUGF~+rM)waUz zpot2opNb!?C=60*<{(d`Q%*eiZbO=rS{`#^l8E2=`FDHm2UIGg;J|9vy1qpaA|VoK zIECd%{q2-laH{-{Z!5?_O^@W6bPezSctnnTR*@dO6z{2GZZ_CI_HHJB68`u3I{zcH z-u7VA)Vt$E@ZlAsxrg^WlRHdixZbvhcQF96Vqq)i)!Ak*ho1{GDxixZfMnR+50fFr zS=WghXgE;$`6Pv;qxY}ot*$rvBTMZ>Cz7VTv7f9_pehA;IsGF>RJ~hrr;~1Is9hm# zvg?pHeTo_R?fiHA{$HLh&%ra{uQM>1)3|gIH0^PI)x)G}*e*oy%OJvUW5NGifi&OSm+)ESAr1Xo?-z0 zTI2+ZxkeAta*zQJpF0t%vu-e6KpC{jCwuTOeFtc=7Y&Ps@vzI-7C>`{maqc5jS}^| zHLmaa4mGBkg>aWDb_DUc8&KMN`1>Sfs4?;4uu*JLpo7nj+I(2UGy0hLnFdDk1pF0n zau(DnKPdh+&;LROvX(=pi^_;x<}*lAd1rDp_u8FHBOHn)h+LXpYG+CE0mdJ!Y7D{! zMtL>yuT@W#xxg0>NwKgVmkwjo7PSZ66x1);p{Z%|K}$qg@FTg-onw4U^80yC+<&=7v{MW+oS zFNK$EWMpx8aH@n#=SIP)K*O%CvIv0%1-gp49mBWrEc!dBCWa)6 zC#}`Fb>+WtEQW1pNjq^j&d1_Ai)RUe1{uDe-j@2GnU7BS{LZ?D+WT3CJ_F)pwfejz ztM7R_D={>{(wIMw*z7#T6+DekdU0e$z!IW>lR?)UHrgKNF5?E*M#0GyioXe6z&g)- zC{}T0@9<^2ZWN9VVxMaJMKxP{`9(0CfvK!V(i)Z{LI~zS66ixDMJp0a=yDq);n~{Y zr2#LfJ-hO#Gb2<7)C0XA3)`%av`6c2aT2oU!MzUjiSlk~gYiRhxG&0@lKRvvW6k&i z1G(;DwsU2n$w7d+QrnJNHKR1uIWXSc=N9w@#vWfcDfHtuW8&=al~@iIHO_yYwxlo~o6cYzJM{lVUEiuKK&Balyb$Y7&n|Uev!02_W4)itq!)Z16Tb9tyRhq3t>T`e zynZ^gK6HzEdEXTlvRsPHC!F$}VcEa(N}fEhWg=ZfSYxo==JwMsN}8Ft%-J(h&bh}F|=>- zktMYN8u@#sv6rKq4@mr_vw879L4L?CtU&p9%kgHI0|OUp&KYTaIqwm7Jucz$1Nr++`ZRYJj27|+kQx!M0? zq4z=P3QZ}PRp;%1@k%*`O`IQ3FAqECpI6E|Wl-v4`%hwLg5uGPHJyMz_;D4Tj)0|H z&HZTad8$+9_|p91p+_+wO_@P;I87=%5Y=yoezqZ1bVu|r1oO3rbjDoQCS<`(f?G4G z#63E2h-n!LZD}dw0;?@p6f^hf4B(=H0?;0svcrgCC`RPVB~n0E48o zxn;9p?8YC{0{g?Lpg#Qi+3z3a>9O4H_pZU8|HKpfQr_<`VZ5MUdM9h_mOK&5op?m{ zHFSn#R!||tueQsQrr6)FFmS{Yb*%5IBN&hJbqy}vtOzZ{S1Q;1HNxX5l)4SRy|AG?(l+gnn zj{GP_L?M*ob56b`1J4W{HDyjS?|DYJmHnf{my9gobJyASIB=D`qn<85nUBN4@Ogxi zmX=&`Fy~RIXA76-XWl2DLr$Isu-!Dx5Eav zbQ1W&&dRlh<=&=6)($m}45X$*zViKd#^MO#@yCvFOtwVD>;g;LiINq<-fc6~+>qi0 zSOU16|Y zo{>Z{V<=4lPfS|C5&=JpO8X8Ts^*>}oV$$zE2$Md@eBkhw(y^-!T*OSn$imLk0prMvMH3vlH@Uiak^+tgzF8diX{J3uu?}e0kdq^ z1<(E3aDLPowm%RX$<(KJZT)e}LZLfYVC-Izy}l&Lx?KbjNBc_`jG4=re9;?=&c%1}t$^jC3zoUx(H`mM+uyhZ z8#0>b3}93#I4>)5BG*iR(ztcTD$n~eT1ZpEtq_gE2!?8C`~`L?Hx6c}UYZxYwdZ7( zc;(~scD=h@ricvuJk>9PEeA#p`td)rauxOgj4tf|b5Tj2x;-5CdeE9hT~)}hm2`1` z2OLc-&=2L-=5AwvYUR(qus@P;0pJn}xIFoSh-XZr=o{nj_$UK}DK?%Lkwpg0aC`1b zY$dl^@OI>fIQ{lpz7BB?sop~etyldl9) zoEmUtgmEKv0tGk^L1EU~$PCO^n6M}d8N1Xp${oLCl{V!xa#~x!K0TG10lHOR4hd0j zdc*M$?ufr164@ZFdFeII`G6_oC@LcJFar=a1ZZ};59b#YY^)FUma7k~zft3TgM0l+ z=SP&a@>U-=c2~=zF55Zt1}mHSO9*+0y&-Z6BLlFyAM`QvqUmqtmw&8@H$h+d%T!L% z!7HK=VJC7_YhQr@hIrm9?pTCBUYjw<172Cz%u|})Yr&!f_6;e9daAnXPORikbj%LO zI-<9l`#DGef;HK7%{m{GU8h*uUW9bJa>J3ST-mz4-!w7i#M*vNI=>Sg?(vg1I^cg= zC{k_gwc+Uxr_f~+s*$^42~yYS{9eaBH&Jq|b;zx!3cxf0iI|T6%>Fb6$Qo9~SZS|R z#T%cs2NV@sp$dbQ3VTdTPn^j0!YSt|uZ>1I zbyW(L^#d;+iOybgp!Fy7^uo}857M7D`L%7e|K@G{67-kzdAWdp*Ce#%B~w``Ry9@5 zt=#e0=$CS|GiYnmAv;>Pd0+6Oi7z-$NH3nO&U3w>4pxu-&DdQz_AN0>^x92rvu9?y zjMoguempbHA_oCIXTw>t=9qD3UHmRU*6%Z}v~Nqq2v*23%W$D_Z^i< zc(usnA-Nd0f-w~X&Ge^dX?X+#jBVDXNEzcVqgnXOS)_;2qA%#0piF3zi8_yk&f?c- zr8eRGqETnv_-BTQf-NEz9QZwNTuHBRMnk8i@gsZO{~GfIt7y7ttnC=LA9zcq$zt45 za+J~X&T*>VoNBz@ajtX$AK+@8JqPB$2!a(08WcsU;&o=bCPem86pPB9&=t^#lqq%Q z_689oG24+OFsjLwtf1$CNl_jmv`m~- zURPd@1r|&bhtl`d^1dbzWSDQAgE^!t{>qk^f*Z-kZ*e~sE3OGLw%J~JHlYot{Yt3t z*xt%S=0_!2o`9ZOQ5>&jL`8?_6Vn7VDHc5gNA6hdGXEXKVXQ)k-c-d15}Q-7l)n2a z>PBL!HBq4YfjgT?Y0SANZQScXa;GdOhDM+_QCyB>_q+E(Co0S*$~XUK=CY1yZk_V% z+FWpjO&>0~yOkW;S&nJ5a9KAAvAo_nmn`HK?G4r)y7ak+8Jfn{W5cvJhG>!p3^rAm zL@Cf@T~&0I(PACWvBX;&EAjvlT-vVb(k7EiPV3EUA+RLu_NNisa}A&%DywTv%7+&R zgVygl3TV0-jmY+>6iuJ*Z!94Pq3RK+hY^ow=B2DvJbVl?LjOdKg?~Sf_Nvd%I z)wA@i*98@-lfjjyLG@1;d_s(ua&qnQs)YZ{@HmOSWMA5ieep^3jIgPwZIs3P!0Gx2 z)7Ntg-U)(q{!yZzKh`{*R9v>l{VIZGS9p7gc)m?| zK4v>lN7Qg8ojEw&QP(teoU`{^PlNsqosoL^+pNjGaOE%r%4nz! z4|~WqsOKdVqjEO z=heisSAXA4bRlN>)heZcjSeO&ooZy1esO}BxOz4O2}^^-jm%P`^Q%i_UmqF9`_JHW zO->(Ge7vLgAWBc8)z~R=UusoEzpku8p?B}6)AgH;vP5MJ&aQVz;I4`dt#H*_ICgrYypu7<>GL>#4pkw0%o} zj@N1QucEuFk+GlZZ@G<(RY0b&{ph$Yn0??KG>^@HW;5{NLxk5X^bmrV(}CjakHi$7 zL+^!w?eEv*^znxX7uqeVWLTA6wRmq%P5$QXvdt$kYSKmF4>T0k@Jx|6W5Ry@LtHhU zfMK9^CQg(8BZE3XlmI}ka@=AUmsdk{Y4{j{5%4BIb`}1!FlgekCMYC47w6qAg7n~d z5lGnUuKbI6mp(IFR7zOZ7&NN!_Ou$A_B2R3PrJK?#q5#^U-`O{Mq)y783)6lFVZ@T zjar;L;8UMO?7)DH0bm?;#eM=#PWK0fIN;yN_yx%H1=mkq#lZ<0`!4p8zUN~1)(Gj^ z{tnMjIA`#kT~w)+>6RwOYIw&2874|8fV%qRm%S*Wi!=Tcmqy&4>T}cg9Y8Y=33IcK zL>!`J9b^1wcE}+lj>=o2=!wh9L)L!jg7}PQZ??s+Ib8MY(N3#Rumf$UH__poLyJ@b zA_-zB-%xyr~zPVkZenug3b~^bvyYakiVt4Ha;N zt>44w(eG01$R9^Vrf`k4h1%HccmC5}j4-qqgikv7_&+myMxW+zACf;d_Y~w;oPtms zXg!hs@OXsP|H|LmKMK>QhD)PWb!%-7^z?ngG9udBPH!ux%vGu{o=v44J`ktp#-_md z7at0rBF-!S$>2W!n5V`0{Jf+p2xyvgv!+6mXuHGUsQ8yg`X^#>rl(kkP+2IJm)CA@ zJZDW=5apt@`972|2;3@N$5XIv(HTm8 z^Gs^VotW6V_DF{Lqb}Z&$#qs%i@TPuiG17V6ogg&#v9BX@UK3?YreH9iQd+0YXP>w zvX&r-o$IrAVCc=#|I8ASLB8G6kNW=4ZE7$6W+1ttbV29#Ny(eGj4%d|sg*hn9w%h{cif!Yb>6fi-Vk_F6VqS#$4fJ-a{>KC#fXmx{^)4wbI2M+ z078lt`Wx?wqLm`~g*X&!^gGC;2yzs#SBRNLw@Nj5M8$NczE$J0mTWKpPkvhbFFlj7 zI?Hh3l-ZHZi$pd4`sH-7DyCN`u6oY0s?jhGcaR+oZ8>T{Jn-#(Gvx4QK1Fg)aAZ)&3DXy*2O6o)r#~BcsEF zr70BS47)9Qkc+K{Gyp1?CvCGnofs#pH*nOeRJyBjQlr^Y!S@OZQa3CtgASGu(Vq=i z8iB)}`M2bT>TgluGR66_pL$OmI@nIM(bx%se6>CN_Wqy^AMv#KqG>K+gWa{ zFnETKf|A8)VYmx-Ql-2eb6EcYwoii#kf6zV7H!)pDf<1B?Xn!q(D&*k!qSTE6F}Jn z3$a;2K>F-3J>mE|VzLZ7>Nqmn(>4bioroqKzvKP(*(6G6>hQFwF)ex8qF3}Pnl@I~ zx~x$R+~A3XM_w;W_@epFXdXe(-kRTM4R3Q>jzSo(g&nb6U@BIAo+;Zg3Yvi0#2f#a zC7%3@jR>dz4G;s+8;qJK^WE=LZ|Or*z+23^h;#io$cF;Ch0N?eq(1Hf+?1mnSxsoK zmSx5>S;BS&TpovMt35X~nJ`hGpoOFK+W0f;@P8{tWyP$#BfsG~5f80xZxCLBCJZ$u zFE$@Xe-z^59WJ(R`r4iu^I;0%&DWwokom)S&4bspGXDrL9WMu!y5J5db$0#6`o1HA z-|i)%M@bLw>b9Jp1dGUBqEjn_MjaeH07qu-i%-@KhCE%O9@ZaUGZoSP$U_sbz{v~Z+!x!PdZXSP>b8`9{v1-;@_kwq% z7jfU|u{?`=CV*ZYrx^x#_tj>O#_#EH3-HL6u8p&F=7udO2|K9d@4zHn*Pv|nCcXiHY#KvYxI-7Ieur&M%w%iQZF`K{;hPiHiX zic`aF*4)nTLHZ=RYtow(OPhv+`)L&P(GbO4|x9~mLF2E*^YaW;?J`V-}L z<8|<7--9fjVR*$;@xU3s1A9A=as<$?_;;^N~gYBGae+}IF&wgW$18fWR zr@F)ziRXEq=0#O?v+b|*UD6D)lIDrzgr2B+?gri{k)Y2@bch{UHyHUlW1FB_rRxzT7-flZD<=v~>cKL@D&WVOn6;Fr%Vz0v)t}O*`&HN$a?-rGpIP>u%b|jfuso z3o%W5vGw(nHlvWHQ?qDHhVJvATqhS9{sK*7Vp3K)uZdyO1Ga5#6(&o10ifEn7rRk5Xq^8auJS}I3hC#`CA)=;4L)i6dxWyfXpe@ zxhnIBRUl$#G$~x$nI>i6e%9wpnwn^TdlDzm{#7)4GBg`~fBp)0h` zeW*} zSh1urbcQA}pfC>t9EL|PhX)Sa75Je0Oo5ygjE3r8Y|R(`LJ-Xkr~$?@Ak)!Z z!{83X$5@p6Hs!IfUyE@-!55lzntw{GFAMGmm;NLs8li34nhe-klovipD1IF9>F%Gb z@M*$N6n^7(L71wP6vzr>4dow1jbrQoPgls>4D=ecN-@UDTpdgMQV>gLLWbe=1&8d| zC#Zv6l8An=4D_XAML-6O{hiU2I22av&vCq16;B>vqB=bM;^l`dWZpD_#_|@QZA7R2 ze>xD}U^l=JX*YXce!JuNr7R0;;PPrYo<(KB%XZ&y^SczfZ=p|oHCKeX5Kp_1rm*|fi7mv{q zTr@j#X7}dPTiuXAfKHX`MRCKbODZYrBkLHSHx1lF3~x)#=|9;7CseN4z7u!ZoOnbp zAse(579>5|Y#xh0ptN*8E^|y&Hpb4(4DwiWNfK93<>|_LTX*Ch6(U+$$qIq;-${G-Jf!T1k_fq-;^Sq41uz#TglSM1d0>=Ra6{ z_?J^U#Z{<%oLP}Iv2ubOlR<=imv&>0eB-4c4v0FNQfO+CXMJvS8zy2p3v*tJ!I!T; z>4=8r!gjt$W}ng88?%a=%uk4pbd_4()pXrhO}@hx`K08>8j^mf_xJ%!0;; zTF8oPl&QlPtvv!7d2mU<-#0*e7#-ul;-H}2h<{e9mycdEb5t~u3L+kMS{{}xddg%qd z#YyT`D>|ewEUCPwoqWw|OZDDFqj`-CCc4G^p}J0T(IR#M`H)tzu1fyL8tGFQ>VF3N z2!Q*)Ok`IDvvewG*3sjusYn?pR7n_jkCnH;BB?!M%bQ55i^7ch&OxbFL2_g9>Yri@ z1|3T2rDcx2SVtmVPF9+h2-T#^`NL`jxoZfKs19)(pqEve?vvN(Nrd$dQ*-F0+B{J-u>Nt3bX2PpLb$**Jh4(l!}TTuLxd>x0)v%XG4bKUt{`-zMAIB zoH*+?sXWf@L@Rdz__mboOFF@Qp9(^V0fpeu7N+cKf)4CsZ<0b{InrkCwO9Jf@Hkg5 zYlIkw2v`2&EFgG^9=73aj^L2Qph-BJ$5IivyDiu>nYr}UGyTCMe#sAQb$>II_(c=p zX+R(?HnN^j52%LArlHO8-EZtw#Q2PNc_kC)$T1z^I**-ggJLgHk%_Q|KrgAu+L6zf z3UT+jTEG>qg+8E|d1?Qf?+JiJM+c>Ntm9LLCjV}L1K%-!cz=4BrIGa$WmxXsoW!jFVM|M1_Q7o3<4dR~8P*$)0uM>n_!PzCZP& zw!^WrhK{`*0-;*P72ghdkoWrlrH%Yn;kH8UADV>YW!Y;dKTK~z&8HuSK=KzelyU3Y zzLeORL@w;`#k8<%k*_947o!J0tuWjxX6@GoC%vZvNg^w4z6-1M1be2r?_Q{2NV}=u ztc{Qo)?kp5{xh0A5C*b(;a1)<1lNYI+4l>xD=`BxUaa|Lp&wgsbymy2Mbd1@$oS~r zN^JWAu%a7n^PZS!{I}P-X+wZ)7G{EUR$|P<-<%$#;wU5)T!Dn^zsYZn>yrGUfP;lY zQ=_vNjBinztc>$kKPhc?&Jz{{VrC`jT5_Lc3wJMtyD5UooDDoPVOUcoOJbq8NwL^+{{_)6 zg@`{@R;f;owgrix?zrE!z+M+We#AmwZVf{5;N%2@ zuJ5UX&vPmgLLsh&h8m%)zugYwb)A||EFf#KoEK_nh6JAIO6_$sR)2^u=6*hl_m9U) z7qg>OQU6Ua)01B2Fg~JyZ`$IK5Le6?B2W=2X*M^ZS!gEGG>qm|n9=-=`c9RRqZ86m zo@+z&q?YbYt}sf|jQI~l*W7s@1BW73(i}0z`v*0AU+mv0Lh+{jyj>hkzvjLdVqT$# z6H0W3PN~h9g1csy#+IALr^Vp@Fh#8a;t8WYL4o)3KxK!l0WdmDiObNcH+kAbPpHMBtmQcVny|7FHJP$aLe4vcLjuweB`Ue_@unOY|qEM$5HB;qMU_S zVA&z>&Slu#{gBa-xFy}xPsw|x75b9EvLg}l=A>5j>W>w7gr5W<8QfgX98MVLy1kJ^ zIS&(6?a^Uu0o7wSenv=fnD>^K8$?jzn1Bv@NJuQ%Fso<%O%F5uEJ6>$rVs3oNtzOx zh?@AbLA=KS+E|&`U&(?F>5!kI6Qtp(J(Ai~?v>$dEfJ&0B~SSIEYGv<2UXNl8I<9o z2YpC_7Py`WJwH2opjVBNt0w|gv_6t0cuXK09@}Pyj=IgU4qbEO{F5 z6ss*3l#5!r!`Di6usJK65C5Ip(CSrh+WcLfIcROpkrf6j9InxO z>LOeNnt9Ua(EG5D<=SRuOClNPi@}|i7i4WcxP>F4H~5b7X@-YStyWXv$JjL0air51 zRA2)Y2x$HP6>q%I$^^rRGSDBlcqI`GW~;t^n`0nhB{li?2>D`$g5FkMH#mk9+`qPiC5s zc@D`sEA^2|_aH`*A=`Mmb9bKKVgjd%RndY>Yu_HCj0L?n@wSb0;I*$r#U3F&^QyBP z*v)z9vE~iitiTdZw6sv5qouC;v)J2E`Vo|w^_V~BNc*e9#(N|B2`&t2i*U`nma5$c zt~3$0llSe=U%biy!NENOzawAshfuU`ZX0}}ui&auh}DoByt}zwsd+D*SXkI%j7rW6 zU0$#0XKL^z)Z8*1xuJyNB|_-s$C{ zQpZVq8Qc(HiDDGqJ(U6Y-xQkEors8}L$K1LX9WeLLbOq2S_+)*TFOgTE|rW!~9fu9Yv|883zVEzq5ZtQUGt96f?9B|ZE?!?1A zmonNJmH9c$HUk~Yn+-|tUkz=RzU7#-cHRjV4;fw9_q#mD$M*`SagXT|k^F?82tu=38ak{FKti;#uH>PD>+ZV=nIK=Vh4qA!PT60gm8cX2?xRQkd zBZr|BlAck`dcKr&1%5yEY+I}6NPG<10EU2P3l~p`#OxzyKoe;;UBQo}>~3Em=f%mr zugO_zb+#xloE>GsP*iG7bfF`OSABygTf15+K2sMv@8PSUE=hFR&3UsbLl!PNk$h+Ue`bHPN4}pH^EAG-W2ePl z<&$ulu;R+_^_Bg8`9|fSho*X7cjfqkjrKPcprk8ZeDv+%5aVDUzW0$wK@Ctwiua__ zcwc_nG6}7S1GJf$Wu9{E=kagWALtSKiSV(4a6tRM5Ufdya?!DtnNK;-JU$gC2?QV<=Ke^${8RJ zmYg^z@FfcG6a`G-_&5cyjVi4+H@#mn?{{Idt7xw;2R~yZt1}?klKwdeYJ{3PNyw7- z8Qb&y@9~5|Dr9p>49OkZn;O{*W5@^{@Ss*`%@bAx6h^oL;XJ7RFa;A#W|}Dh>Hwp5 zbwxqtZ&?CBRw{%}t2QTdlGh>uF_DQT=-A3H>|}@8mEI^fiRN>et|pzv`{?gvfUuK! z(rnoEV)UMgu^U|GjJh~}?JM^;9$QbZmC*2wHh14f-V!$5sd`f}X`_TFhM?xQtVcqA z^Ic)Muiqmp^amR;>Ee}D$de}1LlF7=%AAi5(gZaCnFzP=-j^#zmPE91%<{IG=DtoT zm#Fje?}~Y_vl<#VuX-gCEwsBaB_(V4-P}ym67+cDqP@e!8WH8|>OW;($>1djeg(pn zL)l!kz#E`bEBHf`GU2GNLf~&iTt$QvL=OGT_{pUO)#tYhbB|U@|E84SR9!|{&K}QQ zrr-%!yS6q{06t*1yHt82e3MlY;ed;cl?8{ZjtR`4`3CA6dbxMwN(rC9&Zb#W*{iqI z=tnB2TYFmPI(^`Y@fahIr{Do<*T0TgqR8;>%9NY*l~EbOKU3t|ddN(Ffv`4qE0Bd0 zKn_8n(02Wq{2iFTWb>r0IF(c~O(_4>WF{Hhu=DZ~1{8THds6fDD z@9BzJHiNXLkOL_Fuw5IO%B3WGlhoIaQ@c)%Io@FHmmu?Q3-y<2i<%s&#h`VKq2^Sz z_t&BgeNn%^pXgWkXziPuF?+J}f0e4f`LW0R;B6(J_5$yKs0a6Yi&k)2=Rdoi7l_ad|m7g z)6k$)(Pm2Y%N;*X*vT+y^g^t=DrWe@{zFz9F%%M%b#r%WtjjEXp&#zw?oo7^Jb z_7tyI5EZc%tViSS5M(eV6pVZAn)MV14C|D~`n~98v?c)HCxxj$Z#hgQabd2`kt&)U zjdno+0-7;sdwf0CH3M&z0w{c3VZ3#PKZ`Jp+vBRWnmJTSv@{m#Me&O@b}39tZDjPt zr_P<6@CE4BJerBPFmtmJJJ_@&D8XJdQ`Qdx)P`%KAqYpP9@z7xKm;+7FW4s|Nc z?KL4!39%@0rTHMj`UqTDWU{ORoH|cAb>=#K z){t($ulDlW!P2Dj4<2^PjUT&G!9Um#aB?}v^SW^O#DKRSQ84~ed#L|J9})jVzP4|| zu=)CET@CzKVc|pPC|Cc1W&JBPtY@NKU%BmGo#471tIj%QS@~)zhKv}o+1#XsL#r;Z zXYnb10+tlS_2f;ILPKKQ`7B0O?1Vk`@JEaNxU+$OHnB1lj6P*(_1&2-SawGf{%Z6| zS-HCySK2q(;q>^0vcVGtm5P}1_MqH?_cr4OE!znRLL!=+w_nes+0AP`QIW)Icd7}i zdbKqSnZodcr?1LN-jcPbZwNnmNLV54P}IYY6vmw1o`FpxcbTw-{({mwUQF)I_~9yu zN^+UzGxg*5h?UhT-x+E>x>EfuGxMzTFlY{+*2Ur%y|e4AY4E0BqEH9c@oVG$ASQ-R zkO_zL!^C(Vt*d123YqqmFe}{ZF0%TXEiI5=)}&{bFkTg5{MYd!{&AgH5Sbr-`$~*r z>J&@c!4hF_c_|MSRDeZQzFy)Tvya;V3rqyh_Hg6J_$M@G&UB9CEo9)rCQL55 zZt28Ok%?MHd3{9G%lLvEe@9l}fJtF7XQaX1mFpXAXx7WiD2j{t%#rxOc7IKRoLBBR zR?=ldPO~z<_N?owkG(#)S7-53^hO{@4s$ZXJZVdHonCvAP1G*&q2q;!ml>f2h58D^ z1)%hy2&$E|Z%Q52-&G!0>CNf+e7aoQbSC{%smL@(qYoR`4I47$lNQVYYSMt;elNj> zZg!f$l>9%}X$Gv3KRUWrYekx-Q|9!=+M#7Ia%$&MZ^->jM%SzbOor}P#T+CSQM(MY zAO+X{zWe*swXj0oOX-v?n!`Sop##f=cj}^LU{yNOOgPJp&9;Y$QjP?Zx;mP8t?kVQ zz2gF!fUf-1>Gkb!*E1js&+X6(;r+%OVcvlnX3Di{WQSs!96fsaQ|%e1#gm|#}*z}{1SEp&T#*q{2Gt7B+0m*I;T zrzWpg5g%`>=&Fioc_>`K2Gl!ctyQ`5i>OhfKBR*pI{Sgvgvjxjsat5O@j!pCPF>w? zueztGK6gi(IDvHPrNm5Us(RQA zDz4Xu+!y~DTkx=aT(05a$B(S)9`b;JM9~EUrTM1gha|IjwcP6EW7!4$&2&$}pE`F< zJF2by%|PB_a5Ynskw?LPBKjHH5?P4hOS=G|#-S6uusjOEdJrea4?D z^%h{$?tPPCv4oN+;3D1QWyPYg14XI zKDF82Y$2qV+6GfnY&md9LMUUme*J)+f7@-hmFzRqMFXjv%idu^xL29yh%zj5%kLE8_}JL z)o~f~htV2_^5k)MNTCd1)J$txb_SCj(_MKkwsZqsOi85q*Wf53$(AF^-DYknU{t|z zf-NuTt@{l203v@661&S4tp$7LDtMX}eIdc;=7!c2qkr?1M*XnwgVPtN!W>O$m;M$r z&EKeD9cizG|0CI(S^K)8G~qQ}fjC=w;@oX&S8dKBsB>CUA|sOw_& zB3iGhUEBP{SBTf6HH+LM-R-TFCE6FJNJii_R_fQcIJm1&tN3^JM_&m56(5L-DDQuZ zKt}sl@PU2qY1+~ec8+w(QY@{GuUd5VjAs@40oE@xToF+_-S5vS>{uS|C(T})H8JPj z%TZ`)+{n8(lId!b*8BaeN+k7Tx729U6)gX)pIW$Wy5pn6!un5efou3kWZzK zBI^t1?X6%#5$OHp^GNlhcTo6W7KpY-;AN)c~aGivHa%-XFuX4xp7J zf2nsifGB7aeig>sacL*AGt;?;YU@hwuZlYycuTJRX#cSy=3a+w~u{3q($Jn9x>KXN_8%2fWkTVoYn1xfAIw0(srI!J(ay!d0imgC$q9 zn%CToGde5Om^na3A^B{A9gBh@)R*$-Ag#+dvD5vX0e%P&G;_uFA-WU0=ZW5%T%l(_ z{xXR1y~W^r%zk4p2b7LN3~-hZb9TspH7}K!w&e6$mg6UH0Dg~**DoAf{TYS?=@3Rp zCkqBkjHvVU_kK>%4*d=bPV?XWrN1_@m+-5*OL6St$H^@C19$w*x1koiSadOLNn|@) zU#?DNyrO_&^wOasKF&zOVHU*B`zn7i3tz!nOT&gnkD!X_x2^j5&T`dxht0qUv3Bxn&xbFKEoQ)>*f!UA-pbT z9qWV{niFwts5u_jkuwvvHM#*YNI4{4u!X(*hJizZQ#uq?L;S0B(s;{*_i`PP1~m%+ zO9N`j6@5?NtMmu+zpwld|3S>Y@@U@BF?`R8R0y=?mCBg>Pgkf1iV?Zrc1;c+8^zE6 zhIrQSMh6k=JcRnvV~!$zq#rfdLz9R9TVF78M!AqyxVw$jbR^;P=*YsZ$Majt?uk;f zCKKuLT0z_K3caVVp4f?#X?PP4XPAd@m-A-Y)qku#x!+_< z2M5>-CCw_`Lsw<7HxE&$qO)P66_gIT+G1?Y_V7(f^v~EZQdAKJtROScJjkjMaX^y# zLsb8mzJWom-3rYN4H8;TPkD^d1Q4-|EqA!2YPFpVkE4B%7fp|a;vPz+uqLSN#r+=O zD^KgyY@50=x0Tw$ag_QU@i}+8QPD^pAry(&OQH=lL74k^$+)K40 zH!;61_Qe2`I_PmFNJ4K^2bXkt4D4Ju3F{q4AJk`UokM2RC3RShVB%5{><5A!2Jxv& zF-~uPCJK0W$QD1dqXX!4-W|dkB{PTdyVsR%>f#|uO)G$c22bKbA>g=Y|R=pmtXjBbn3((lf+o+GlOPr zWa3RM7DR0pWl~_o!}oBxLPTA6D2{Cm9!q&wq=6AH%`zFU6Vh`yV4*e~ zgpqqHDK)=8MG4!59gdy{f`-jBUT2s2wX1Uq7W5wTu`y4lKBm8NtZYf7D~JFZHB5`> z-Z^iRT!Yhf@;aNe`NBLsex*cLQ8sORtbQ=d6qsX9fT2_Y!V18uBAeY=48^XzLAM0~ z1qojgds^}|BF9seiIc5w=~brPvNtnF9x;=3o)kNDaVg&`_~=bzz#H|l+bXd2GYA*= z+PgLYE1T-~+TRgLx(D+XorUM@|Ls;=d$O?Mt8u0p8?ZoHeK3m;CRj3F1`HJdCTtmg z^_86!${t*v&x^sRW=#@t*QJ2p8#}Lzx z-uJA${lmVasqB*oh+<0Al!;-+OE!(>&v!d@xt_V6Z%1R1jx2h9P;ng6WhnLdy7yBd zaw#fEK|RMVlWZ~Gdb?ErLH`m7o_4}gmvGduiyg~LI`7*SrMf_WpTD$)W-6&*?(!g- zAcfnXbIBx&trawqc^9eXnLLQSWx#{lBJX7Ww_a2B{ZRQl{KcQ-HMZ0#$GV@svwB8Y zvZ!8yut$fbU4j|3eujGGLf?|PEBEYP6S=A05D0iwd-Eo0s%|d57Ua}&p(~ub#68@# zO3KBNP|)ZxGUhW^g1uBNitPjsM?-gtxP54%9gp>3`={eumw@ zy}AwNG69jrpYb@@@3lL#bPt|`qX|Kg;LYBXridQ4AHJygzXjN1#OPS!4jg&E8*_Sb zic7gN`8UG#m?y8vS2SiEXg$4Vjhc*t%%}G6-RG&gg#q=(fgi2G%OvxS8}bk9NK7LJYk_E0(AQxOP`Nr|rinLz`Bz!*H-=8MmK*?71Kp<6qk z-bGa|#x*b9a{16ui!p3X4p;%*grg1LieJT7(Z;6}YsvGWw(#VZW3#vu?=XwXo}IZ{ zaq4T#dFsgEY|MQkyNrduBUw&00^XGV%@`v5a`^L7ZinHsxoISTT^yiu*UW3jM7g{! zU%3rpnJF?{NB_Q&lll)r*)wlVY_sW+^1zb{(9p6&{r3kC0)vQH75XQ;QRFKsKIb#B z^#?kMmDUzx!sUIVGz_?@l-DReEWwKxoxc}7VXHx&?qS)LFz8W_;a8NdKPcEi zoGrO6%crh7h=tjVG=eG)eB>7b8B5z6@7;Wd_4lTYx&few+&&P(XX10OGel>jcFX;x zLyVc7Ge{|uoF)03>`o|5Rrhn3fC0_c+8g0f-&5!lmPpr)bEAO@kkN*xE&+uwyZn!? z1QpQ^GzUFX(3h`0toMKRAjk@z?LfELizuCm=Bn1>`oBvQ7zK=yqK9Gzr)v|hZzl_mjpi~qbnRi&en-UjjoX0_F~7Xxfjz%LUe@NCNb09L z>%Cw8oe_HmFy?jLBbQ5&X2}{0TJXcR#ig~08re53*_$q`{Yd{7`QSFJ_EA5!#gkiu z-)>YTD4pAwA>!c??*7!;?EmIm>3yDnS=UT(S0w|xok)N%Wjk~Rp@>$QB}Y++xl`u@ za$?Y8haxP(3@&|B?zb-*+sl7k=YG`tw~g^&bcD!uyz)})xGI;us&xI(-D!eARJdrR zEB=a}|D-Z!)ar%f8)d_;FBK@{YO&<_yjG`?6%ZtO72>{s1=UKYTf2XeUQuhzRuppz z|H7?Wm(z>lr_7PtvD8@2-%C>nE+nD#eySoL0OJ)tI#I_o{dF&|`xB@^`F6#SnRH}KmDs7557 zxz%+|?(WUxp-B+8_aI1n+jrNV!E*}sVB!6!V0C2><51;ofqj5p#0>n#DbF}ZYt1~^ z?9?kIIN5zw;LG}k?(Rk>vazx5-HF=X%3{he<;_R>lGLCD@rw^io!5}+N3-h^(+fyL zYS-Pjr(a>{9Sa~+7AWGKl<$ttryl8>(LU^Be1mF&%a2B)epLqUK&?2QQ~qG(wBR9f z$<(W0r`>(-b9XlCtAHJh68dgaAir1@MAhFC38^jTRRot-1Dzx{BtDyQe<|7PMtP%M z(MBN?3|X_=wD}9h$XXP9q57mdpGSR=W&49JIys3Bg}_x7_W;*&gJbQ%*G`x=3cHn~ zrB5vERvIPMiq1RJW?Bb97X#?2x~lr-**n*Gyo%q?)u^>0R5y#G4wRKHJyfPx zO^=oZ+X`{IhOFbS4|?vOS;H`j))qUye80BZ)S3xBAUcT`&sl`Rcn-tAn>pj?Q zw=UCoD&S4nx_4r?wSMwaY@MjHdI3HHSQK}**KK)#a2pe`nhV-qmMu&)GK+kNlx@QE*Xa~W}2g%5w25^1~Uu;}eK%g0FgW4_c^st+kl zIS{+Z`IFVW8fu<4@w|i*Lxhyw>Usi8fpADb46l!@I^SmU{Gzh5E}~ErOC%v!ncQVO z9?c7EyXVRNVsM#S{lDA%9*-ZOv~x?J_h5@>Jjh`bYPyFX)QSetLE&;JhVaOzNj;}m zMq3t(H7hVNn){6Z^}h7W!TYfV5>*PPgQDU7Ob%r9T@aB^%edJ$k;-_;RYj zgDc`vXI5nC@>(tateZPdUO6Mm()gU*2;cDA!Y@59TvG0p95yL~%UZu%#WB+?H}{!q zI!m=SN-SIvJ$QPK$K{eo%g?MkDQp~$!y}SwwNg%gVf+>#$S*tJ*^{>cMImhPhU$m0 zgw-4iWc$WjT;jaOM1IvVnjhd-IOH(JefD^Yp`BUiIQqWbR&g>oVE1H@(*g@aMb@)Y zmliT2jhFhKT%#eItu1`v@mC=q+DRp_P%V<~nTaVNfVRgj=%>NrT_$5Ub9Y+e9g+_> zCdvNxq!aN#Aj{4c^r?~B38Q(nILqh_OcpAM7-`29aP;5OGh zPXzss$7+HXHfZoaZx8!F^WK$rh9m+;O1DQRA9>i0^_6ZCdFSzIsJ7MdLySTc@*iJn z#{^6|?`Tb}QX^*bqG9=L(?Vzr!!+5E%TK;UcM*e2SlT}PlT*p~BY)5EB&9jzQrP%E zL5#D+L3!3Wij05KNY?I9U#6dSJJbF|_Q~|Z46NxZ>#raHykhE1thO(=i7Iu$QxO^CUZ0%+T-$40)kj9t~U@Fy}4 z@Ci7UE|6Dvq@vWbHGGr&hoCw#v36)Z53L2J$sk8G_V3kBk>hPhL{I>n#P__I)N~s;9C>PJwRaLvl2O{Y-bOV6IKxN|CF z&$J5+Ra}$Pu9&tph9!@V2f?ZZEPup{%4%qi<{2~#k2Et5<^e4a1u zwiEg~6F9&V;c{;KklxJdL+~__MK`4O58OQ!H55d$vRV|f;H`r7;IX6}pJ1LiW{&p| z%>#LBh`3IB36%ar>XV>6z8_2XiFa(^6Y2N1v)3)3;UkW^eMRJyal#sOf-f z$H{jB@1NIo#}0FhhD!^dYq1KlIbD>bW5*TVtT=euQQL1X+4Px##TpQ|l`c-o zb{U{ORRa@N7_SkDR*x}Evd1Lp*jG!$$Y28m9Kb12Dli3-yV`2;?*6{Fonu^y#?anL zNwtsof&a#!x^JC9P-@NXDW1)rMtblk9a;3!+qZ^GvW8sHIz7#^iJ54W${Xy4OMP1` z7}dd;y$eDTM0a8i|9axCB3FIJ7~-Ci?I*@46t`=;cS2mqvb6U`4**mVwFBp7rJ#0U zYr;xXRa|GT%&`e0Hvw+1op{DVS9Z*8-hNVd`d7oHen&0;Gh3(kOcxa|&R1`)3wjmN zB2Cz&5Zwp(p)XCbALH=z3S?uP!R2fP>2G52k$^ivLHLAXTUWD$5>H`4h9U_G5AT$N z+4g)%K7wC=+`}AaEZ|aNhyPyaWDSQ|SE~4Ani7tvHwj4PT||-gF?0FUUc+Od(;Q6} zv#FS~pQy61+mBBp3^4K)XPu;motM6L3PGoh${>Xg8Q z6aigJ{?(QmUpZrvuv%SLVY|~x&bHAgd%f|e>QN%py!IIaiW+fP+k#dlvtm?N+;m6) zsgK`F#{WByhBm5K-!rt-PZ%qR(}!9S9_Z=qF{h9z73I?v{~uG=0vBWU{v*V)Ml6c9 zL5SZ{VwbYj>$YNDTC9!TG?ZL+kz!Z1>1A1oG?Eotnk6>3m0UxbQkfD$D7kbm6}n7Q zGtI^S`${eRBL%zHWKInVQ)=XRcRPI&=xjOz?a-M-3CUF|z($un<)-zs(#cBY|ccMcubLX(A~z%%mXTTlh;C;m#n-V0W;Jg_T<9ZHV1;WMTIq5o2YLzf1G z&ym{Iix!mg4R7HhgS|FZM#3}_`0SsiN8rhEO`nb^Q=NvWInWc?{z*vNkM2 zhZ;5uPz9lZR-0}(vP!w)ad6sG4}!X;E>1$qmMTnoM-6nD$qQ`r)>?i_>MoKK8ug_b zQI5*Tb**{n*NY83(IZIX659bwhZ9)}c`$j0#tws3mp}ilq^ZKT@ zMJ>(0Uz~(3^BgKam@G0pbo@A9$0m@$@oy9_%=H|(kkN%ced`={Xk@K1AabGdP1DSA zq~)mn9mG|oBj>O6TocrsXLWT$ZtW<6XfS2+7mF*WZET*$UqF`=_VQy~JJwF*Jqp`? zLP3~C`FNq{Yo55HIEBtyL6I~#nhtSlL0acHtKZnI*FBvb&dBNM#xI*&mimnGu(7Go zBWS-3-3iw53!=|tS{?DZx_B|fD0e0VoOD`Bh=ht2f9-y>`!zrGq+yaDu4Mdz_ZTj% zKb1H1?-<=av{hWm>Aj1ME}Ld0$=|5ZANiFEc&VNQ*j#79sIJhdZ_#g*+v7B%uk3G7 z?I<;O#!%>)njNobAbJ!jP%S-Jv<|d+JwM05zY}k;zswI8x!08l&uVM7sAe23Df5pd zm?@yOmx&oD!#oI?y2{9!B3;Rk#0-}i*Lu?m4l4Egoq1Cj;=+SS3jk~5m# ziQ}3^LyJuk%a{y%Gk*Htbt9hK!(ND%5Scx+V5hzEkxsTZT@ALWm4*{@aad-4rf2(+ z>X@?Zpb-WGHq&eG1iyRHk-8h_+H@|DPfHRZW?PDGJ-GPawDnK57H@ZlssD1*ulRnp z^i0P>bQO|+!q5vp42v(_wF-+)Uh}ASUH0}0KiC}D zUQxf*;lb}T{IKZou7u%Sre>BS)x!%!Xm}-xf>r3`Tq`V$fQrty7slt=u)IUAa^bPk z`W1myLLHsz^!J=*{2sMR*R+^2I|5a;!BGc>v>PNySwU*POjugjWY}===RqB`mFOD- z=0H;kl>Sk-1(Jo8!1ga%qgi;7D;n~gzi6qpTML;fJcqx|CyftkUbRu!2m`ly{&HtD@#Rk|?F#OMbj{ z!oA>MqiuA9rCv@xFjD{+$1RKJfC0)o8eMe8dM6dm6{;o}=iz4j?vkL*Ro2 zrHcxtEoVRR?mq_>9m{-lM1tL*SibWQ1$&VZ#R5z1El~*3*HtV{W;qV(jqMH()oh9? z9WwVivec-!VIE^4qV?1DC*-8F6=rAm^i|k<^Bb0g4ufzYf=<0DGj?r%{Ri;Br_LhwqvHRD6 z(oTQ{c*oTvFM05Z89@3}pJVi!paC?AXm!<~HW$MOsdTgU#o3c7Jom91`=v$*Xy z>ocns=6`nc{@9X2895tL@xUi;qW6VquFt2r%*>TKq(=8mw0t!xhxgkoRShQ@S(CZn z^Q7s$c}sL}O286VbPW^dMa9ql__0H)qGpp8)b5+J!{BG<9H4I4(jCN40hl#8h%r!i0!WMw_8nV(SCK?(URpG;4% zi5xnj!#R9m80e?|Z_yMIGRJ<&Cv=)+I9ElHg9{CV6ps{)yTRdEBG6ByUQj^`99fB= z1?8-)E3dIvCjTqs|MEfR@C5<5CWm^>g)qW5kpHG^@NyU8`!H>{3B|-pn7Oc8RZrpy z#qP&PZ~ldMv#PgymUJvIPb%=W^RE^5i{Gj#r$=91zD?S{EKYczD{=Xzb6e=AY2xVH zBl@n;hw!n;ym%eska_SnYz`@@zsF7)rt#Kier=%mQ$G1;6$UvQS$TyO$EVmnmZJqH z#N5U1G?tMCIr5BJci4c#H1V`nb))xe>ar=S%5*3dKum@hJ{Q#^f80)+<+3bAm*gh< zso$j+(d-n;v~XvkPnbdbRg~&G)WA1#WBe=Y?s-o&AMS4$BnKPjo9IqNPGo zPIxxu*F>p_hjxa_%p7E3M0(?|N)|vmxGF-R;C3fRfk-Ukc4(>w6y^!5e1lbRReq|GE(2M>-SO3)8$XzM?3zx(k~(nZAQ~9%gPm3tTI$uhMa7{FZF@G&nm;B)*qaov zSzQ`7@)iLC_(FA-x$g`^-IU@dBb}ECxDWfD<>KH0?lx7FAq)fI?^*|{m!fWrtYb+8 zmB?T}PNC~me6r9h)FddC{s_Q|1P~HR+yv=#K_DSksD6vk=ziEjK5~5c6xnRD|%TxvAl*vW6gHQeH#5li5{?_fwo-sQlhxdlKO;4pto|MPs(Uqj>=U0CJ&*sA zZ*^9$KOCc7koWZGpy1q@i+&$uuKj98@Ul&FS2!JBu{*7+!EfGolP2vh^vy@os6PRz;H&wLNOk?T+&VJWiakjEUla}Jp~EMdfu z?ocTtV;GvI6Gc$kD+`4$RdqeNZ0a6nq}9$R7-VEoi#AAJyS}+$%n>m3ns5n^=mX|N zI?IP1m?6dt2E~I)?H9!3gf%jmt_|;X^2XUhq5fV=1B+(~#MWI8=xN=de7jW05hE1T zdhKkfaqeX7&eZX;gnn%b^tKAkWaT}|tzfpwKZcusHZWXN6g-{nWU%ID#X$S@0 zUT=_Wtc=r)%-1e_Qc^7vZ{&lzq7=@@*r z9l3GuCJ*zq4AiM1;2zD)iMk0Zf}Ra-x#puNnlxCKf-L1PREuo;RA{#t@RZ}G<&FxK zGwYUoMS(G2l)n%rtnzH!y0r_bMEhM>;7s2bk7ZNE-uGuZFi#CkOL!~w=OIb`uiv^(k2SC2b2Jyd^PQ?AR|))yD&xpvTEzOn_(5f`329M z0$qE2UU7Fs_Z(}&s>=^%g-A#te&{I%-ccUC;>p%&lg?adoVx&n1~$F-z%%58C9#Af zGJ^9816{W<+eP_bBPh}6z>uQg<2 z@1Awd9;A&?!gKs?k5}dky|A`%b*9drCvTIunb!7r?G|tN4gpjYZI$z&IZyKL`eMEa zz)`))J26)54JHa(Je%?6k);z>w{S-HL>2 zQZv^lP`DTa8+w-ZTVi_>_uM6E7@#`xz%JU({mXF=z9@f>T%moN3qCY_QyB)<4H@10Zs zD4aN|Dm=|mhg~L7@y#bKQEh=Sds~#0Z`A%MIP%a1eHyau#C4v}dt1u#Q6Wy~ZY-~x zv^``&Qz&1|@4%k_ogxt!X?OU8&GbO6jIL6x7V*a|k2`lsKLC@lsY0CSCptS$3V#q$W+mr}Kh>7(h5N=zF8%`W~s-u#$NS`DIo zy2g8&>lGfe@#!3L^B<6zNJaIsBdO(04`z|W1?7rvLlnAM&D%6xwlH7oARno&$#fE5 zRhWVqARL-!rb>(l7(1@MiIEEdra$|nC9pkpQ(x(;oEuDip`xwxd$cUAij@2|{M%cu zrJ^c5U#Qb>>1?K=(PqV`wuyvvG{dD7c#{L33z!kV6KPA!gy4myIo=Imk`}pecN7ju zV<^geBKa=@6gYU^ju5lT#F$TPV*BflbStZ0Y)2+nVW_w&A-0>{>=p;>sisdz|Ib>T z%#=2w7wtA<+vhM6xxM0|IxK?Ji{hM)y)8i=$xAM3>s?_TlHfGH z$zBjy^8DH!{WP~`-1EI5#egC9#`aqWm>G@vk(`=b&46VyZjoe1Ir6jrzUJ92Ni?YH zs_G_3T(r@;#_$cp3^M;q5*876**bpn2NO#2%NVu2+gVv_?;&P@Tm-w-I>qTQ24WJC zO*?nua!65(-8QMqY@{KjTLWI>r)8F1fuU*r>^NV0LNrR@i`aLAuZ}xxwej|NjKLyQ zhYHOzCwOs1Gy;(HR(os-d|Vox#lc^T-&yVnK0Is3x7tluzlJS1ZR~4F{8StoCu{j- zPRCIHD6A3cw9!>bixs4BOcuz+S$b&In~{t5c?|Hv;XEO4*C;yzxLoDVs0|R z!XtL32HzB6f}xWsB0v*j6dE~^pma2l$|@Eq+fAn%J@x*k5`moc@v#H~N?A;4Z^sT8 z(n!q!Liy$~B=xD>zl2ucraTn%I3`!tf+YBWVj&K@`(CWP9{K}c#LSU1KdKv5{hmi$ z{PORb!@I_dk{IhWJUDBTYh%Q2>LTfh!!5CEPFIc5g)Hs+KrjO;o+|!a0Fwj+Zi}|k_|6Te`p+;d zE8)H;>B3^D-D>&tWe1eQkjO`wbD{@TrQbg{*LwUd(W4j zP*lp49x&``468WXg3A3Cm2PUN>5#seedN?jENZp^AMMEHyH&=kcI6~#hq7&Fk9 zKcit#0xxq>817PXgueB7USc@vX3*C6j-SZAcE92UFp4R|IkYNMvujD2z~_d-bNSN# zdz(Ukmo0vOH%#rqzuw?1dG9CmBgakJAJ5(JerJZh@DHkM>n72nKcWB2eLhkeUHxs2 zhSys~HrV`E{d~h&;E)ZNz~DHEKQ`(|%L!HsaNL&&)k2*YZ~aRv0jHY++{6pGTWX(7 zKBt~XvR@b$tHPm=j0?u#VI6aG7f%Hg*NEc1Iws3iP5Y9Q7?hDNvna>i#q%JKn$YLB zt9v%bO-J1rpP^m}7QbL~--HVt!LYpLIysb>e>xLANAo%v5%FY(MDxgmx2HO54a(N* zGm(7?FV=Urhxjc|^%g$#t|U*kM0%}mPiWw7-Mae^ZKU-)joH-p4q-730U%U?ag%KL zj1d^zF45NnM3DhTV&oqS17G8-cWTm$!!^C5E83lt^Y*(9KfmjFUcM>}e@X#}H4g=7xQ1O`m-F)GVN8YSM=vUv^LDr#>RY=x$~XZ%g{xmIW=I#eTB(-VzA^;3w=mIuXPp%mAJ7PF%E*2EzFH2xWmNdd zE}|!K@!9sNJnFa;Xkrxqx3yGfr@U>yUNe%>I&OUyUo>16FsY7ZP+yX&{SC+7gi(5m z46sD{i>`r{)K!YHM4>|82!libOLpyJS!VFLaWzn&$dE>Fe|Y4bHD2*{c!@wk#aG+D zwt4qL@5o^Ku}Wb<8#@pmrF*J(s*`?bEU#_a-sW%Ez?Y1Hly^t=8PUip6b}?cEcZj_ zP?JY>W9F8d-JeeX)A}auanQCuA{W?Yef=@hQbry)94SR&Ojt{^s%sycdl(|!$1>Fl z4vfeoYD-l=SwCibOJ9rVs(SQ0I{E94@y-3IUsD z2AelVFbZp#TNNr61izKv5#3`?dWRQolS@Qh)qAro}*{xuHhZLsi>+59<`| zZ(?X;M(Dazhe55vQHSL=`i)u$xj|fg;&A?sxIV2Em$n4rS(vW*ZF$xqTplDVZ+@@?hJ zVb=mVc<*7Q?5;H$+}-UK>ML12Z*DI5dP$w>mlt zYj|q31l>-<+-XRTzbq_fAHkq!|4LZt4Q|uqVBzT;3 z64R7eNgQ`H-dSKv$xUHppMGi8AJ#qNf8mp=>Ur{`o|%Wo9OJ5ky|&$%7Vw`|NWqR! zB48?#dp!??{6P%XV8-m{>JKIk-tLu~;~ne?lep~S=3b-gmHY^k1Jsvh-#*Sr3aETh ztGUjJsZ$tA%-6Bz5l(PU&10`AlaIQQ5Jwppp*?c8nWOLTEYwnMdy8aelfhnFRePtd z|C_wTS8N|L$e|;fU%mSz|V9gC}t4@#V7YZ~`HHymMw}<^7?kWSe({ZiDGSM!{ z`nlVN8rwPVw#s9uBcj>6!tg)YZO87g_h5vTDmt@Vo7QtT0_hILA)50a7phS$%ILdT z6~n%9nFYGFxw`wY+YK@{?`!^Mg}JzLZ#9r=Iwr8`?!AeH|CkM2B=xiQ5ssl8;4&v| z-3^AYw!{2_|5+JVy6J1$!{w*`=w}dl*e`Qr>x8grN4dmyLDQxdaZT{~OQ-7+E=<|} zt$U>?+TaHZNLq3JhZ;JvQ;gTpgb(3+Bl*B?-$lIQ_ez&^VdfgFG_L4euM|L2Rf=o13$ed;+9ga7c6ZxX_YT0#A+Yf+V53xZQ}xh zq98TdyY{_0oXQLfeF;r><5Q!r>Ev#NUa1fyZQI)#-7$k%S-a)WTRm6T^tN33!K6!w zVLDpzzozBFv|MQm&k3VUnf#0(>uKNi;J{-qOYAI)Q=IwHbp<#wn#^JBErGcpjAjAxW4dK)14d)K)g(ZGt-hw~36@!AD z=f)KVqX4SPlr0xOCO|&ZSB+_k!Gd|!m!3zr`iHVcU)ycvSv&9$mbPp7Rlo?XdBU2{ zr8RN+LiaTh*9so`#s#?PY}smQedOrZPztbbEmy&6i{QGahORw2KAv1b z<@_Is)+qH~#eXf5M2Fmx-<20j&}#PX4<=*yDGy9u5!NsJf76&lU#O({&so#aws#i0 zN^kTE+d`2S&8U^(5y=7k6>NzIry+FNz{TAwcH7F{VHpyV`O*&5)wKO;hIBv1RGy0A z&HQ+e{A1{iL|+-Pamcc$dI>@F&dmMU`?Q!L5&UTwAC5QPs=M7Qt>WH$@voi9p>_3( zF6MS{%02FRvkX=XZ3Q*)mP-u|pQ*p@_P&v)O@NzKVUj0N>Up3w>a1>Y8B%A^{E5am zrfp(-A96%C5=G8RtS|2T<<%7;6WXtrT@!*FD{vvJ!?`IuyW?6OrB|ZpdfzXXb0jFm z4Y_VeWwc^@aNTioBf(F6U~v)w9Uu(LBA|c4h`B_In@^2YgXGA(9Wn`*sQKbGKKWTlGZJhPNp;_e8iyS^c`AGutx*08cGNgt)od%rhg?yEihicXZ{??n~YP2b+^2( z0iH_uXO10g79z^B3<_b~hq_71U&dPhN zFrLL6(Bg0Kz*Hh_7FY<*3NdnZuZt@Ue3|!JVa^OIvFj>wVk++}W)V_=p}XZ@jlM9> z^!zH~I)g08X&z8au5p@Y0!WUr39wU}2bCR^0~XVQoDIR#ZwS~F*OMeD+5UGDqh;ga zD<_R8g5UUe0}}*ww3@rLxBCqUJ$+@hl>S3eoDb9lz(f=}ScEO*t{8stXSZ;BgY?rX z0h*NGyN4w`W^!#i5L%gP1jaN)estU{qn))AAGw|)Dyc|FYk zr*`U)%F2yiiLRqpM{Q5}vqqPxudMhZyROn9Q!x_$x#Rde|B=LOU^1soIp*IX7mCKY zSITM|5Sgx*+V`GaxLs&WQyq6*nGdc+)AzN@rp7$K*%VCTLXns_XJ@A9rE7(U2GdGF zO@C+Z{tWAA^Fm^cMf z&r;HXDI%CCg=;Udo@8W}8bX|s`(o*Z+ZK}Gh6p#BKts`c&vK~IVUdD|0u?qR7D-c* z$S=%P9FhYepMgqyee?)(F?81l*NW}z>-C;E;S6erQk5LpviaOgi2^;u?*jjeISXwV z^aEF9T00}n(fWKK@6I6JQCl%f;qSA}<1dB*GupTyZ`bkeurW%^+5tQ>#;M9eQG)hW zbDs$AX4ByD`%5InN%?F;H>dJ+l5NLrO0nZ$gBjpF(UqU!VGSa_=0;+N&I^@w0dAkz zB@XS(-~LJO2d7B48hwZN;VsHLtfF=3=R@MlmO?n@8?r62Jxmq{xIQr?urRmM_o*9#Vnzw9 zYp#sI+z08jRDNe9<(Ls;7k5nRE5CZ7`AgUj-_Yo?#-YVMrg;1fE2s9Lo+Fa{aPwWK z%gZ$Oi~9N)AGpk$OHa*$T@vbeF)nqfK#juX-J!OGkPJWTm4F zMkcqQ+y=@atDnCUT+Ft7nOjrP>OJF2A)l$+)+wb!{x<|RpD2O25P?etcB(fS zUU77>vG!?O0xI@tYQVZB6nCC79=q-VNchRaT;&X-;)mZf7InZ%=HtoF?6@xc5n5V> zE^WKGQ;rP6q9eMDj)#`F?AXHShs{rRS5G}CimEFMvk|DG({!03c>ZT6i+64y$Sp1*D`_#|ySYae+wIk(-e=zZV3HVAy#uwYRut{Td_9o09#+G#>2#55* z$0ekk@mA~Mpx|VWx$ef7s`It!>rTXaqXYN^0U1}=iC$*7Z$8p?e~ZBhP77N+RBw&( zMgje3svKB-J4V1=eB5t>P^i#Z$2qP1NhgZmocqM>@7lyaS6x*{bzs9=<&^lO`q0`> zA5Q}Ddik_TRAs-Lhx%g4?H&E1vW(w?R`+ohYP=OXAwdzg_Qn0kAdYZfBQ=7Xdt$M( z!_Zgyg}^_-`%|l7t~^l?*^Og`mde)O%^MgzxAiYr-H0}5~uSXKDRXBNQyFF-7Ui|zgo%o%3u22vA`@Ll6#BUB9 zS!ZRiwOYMD67gh+POaj+wQSw6UKBv}LM!M|bBlkjK2}%DSvZ}-hO491%AY03`j#Lw zsC$Ru#>j|0h%eK6S9nNC~@T-v;NhuZadzxi+i46 zBO$MqCCG$m~nz|&=H^fu+O_nPH!rAt%6dA-r!%)E+4`p3T`DA z?P>1o)?PxCkKV&=-01V_npFIBTc6#g`c*JjUOP|Z9azZe40rqUv>!SE31a*Sc+c`| zz-Hwck)*m28T*NA5tG^Cr>&zlvaZ~2dF3*{)}rbrL$uB$Smn4*I{#~j?H?r$;N&{u z`GJN;iors1(ZErY*as=LO@XjDG;4iC|~s zL$ugU$O&e_gM1*%sb1+@sjS<|oi@P3Z~FttLPD;hS1a4s#~x4EoT_+~8@r{ds+*0` zgKEAQ(#cB(d!Sj>^y#EG%YO`V9Bw_m(=_Z5L><<*bh_<$N$=IMoaouMF0}F~Ol#KF zd$(!6mCV&^_YRAvm@a?@g+H54Le7+BwWo^EV8WavmeWH*6x}xusU>f*eC&x63<;)a z;I1|!{Ae7DK4dJ9N`9eUgaLgw1yol-HX>q6?5sYNS#pCuDLB{Sj){k*Un zNbktY_V$@OCKioT$+N(QWhTT7Twx2@R#fichH^N)EI775Nf>=f+DPc48z|c+<}A6{ zF+$ALeLgm>OwyO;MT01cGtL(qDcS?`f=@mn5*lmEpoks(dC+fdL0Q|!*gjg(WoB^& za{vII#RrqKSBglIQd#TM2~)y^Yfh7s9f|bX)P)r)iyVncx*>c!FRGGcQr|EhJm_ObGO~t-O;VU z)FV@3#P9eLIYjEA4bJEa=05dXU2#32dH46@{Gd z{TCPUZu8C!q-gSyXTi_yKe{7;TY6#SNai8~ME?U*h%r!_r*`xPsx9?s$b|h#uxN#L=ZMkN3A}vD0=juBxnixeXoUf_7leEj9JmN)(!6}H{H|j zveDB>d)v>cchBuF&Ct)Ly7pUt%i*X|PsdeHAi6_$fbPp}y)`p1pMj!!bwb(*Kgc7?_TUyKNRL3vlWllNp+m%YJ#LQCFQ%>7{UwT`tl>FkRk?u_LWuF)oH zo#q!YfFm|m_~Ei(s{I5bi1Zv4bkiu=9RB3$9o@BV#$+3Gsx_7u;4e;lj=8Xgt9)Yn z`%Ib;CrMMVR?Mc^?-I#M$71Uh7$_;*$wotQZf}9r$%-=m(umNt&Nt;kWhKVc8({Yb zedS7{DWwlu$wVZf79VVyXl$lk($=v%TdtAADi&jq3nuYQ{E16Vh1c6dr%imjb&xQy z?A`htZf0#Dny~qXz|FQY)uWz9zQq+?%^puCA2Z{>3?VBB#pA#b?BC*fp|nE>3PKn< zd1qK+cppY2szIk83EwCFhB%OWst{gH!8olD4{EZpZGF zhI8J(D9hr4kK={iPhofVLsw~~TI;{K?QVq6khb%C!Vg$Egrojr zeyLi*QhcF?9ano3J5$ziHe{*w`MD3JNr{5u4GylV z>*AXtoAib+A!b-p)ix_h9BVpM!fNcVA92t)n(_-Kasl57gmw9>OZWbghqRS4EZ9#* zWE(wdU6fP+K%qI-2^3BhM9W*>Pj>KZXIJ>qSJj}R8G%`;N?g|wL*F0%M{GxrI{Qv% ze3hup?|w4U_qVU;ANXG;@^rR8Ow5+EjvZ{sZev z_)D&oV>6P20~Ynv)c0Q%HZ@hA>>toQdu;+%9MSBwN2Wy6!o?` zB)Qx5OrjUmJ)h1|t~vN`?B~=3tBpB*0k`OQP(}OmmeK&eh_f%W^tHILX`@xYiuL?1 z>@4xtB@`3V@duw&`ikn=arL@)o5e#1MU>st4d#pX1D{1InYpug^9rAb;WI$o&(Y)d z@?VdcFMqBB=S>nftVMa!&0)pkX_RwH<4?)KB zvlb*Z@)CF8vEiWfO(d6oz{Qzf4FjITH1c9TwM5A$ql$Od;W1wz6oViK_uy#<=tgIf zK^0oqvbJ*=peA{6E@AntWe7HkF<7~xa1Xn!3Hf5;3S8+yiXUu=&UlY9hSmAh-tpX; z{%pRr#BSCgmTLkG>LSOxaDali{12marEpa9^u7LlZ3Q|0dUS1#LI&^842E{z`5Q5` zt{Y`GHUcN<9_IF06Az<+qIuZ7bt1qlkpVafdlh<0 z^7KN%RM$C%Zr&Aa|LrPG@{ygOJI5@)Qp3&@~Rh2|T0iHJ`*jDoJ zTPH5_EHAIWxB-5DIclQWwC@ghCv15~U4?)x`TlB8) znR#I7tTi_PGbq-7P2-q(U1iWoNnTU2S}kBypCCdbkvzyf*Pqscpfp$KUVWn`49nhe zB`M?I+s2%FxfL2b32gH1R}Le06fDPrclENXV=-}-@Q!!@r8U0jX75KDG9`rf zBrnL@7Q(n|-)*aiFa9KO#eR#zBzV|7qOK3le?Bjs$5Ct+FefnxA*F3t129*MxkTm{ zv&EQnZ~CZ?X4q085n|}SFl3tJl{<1!&t894;79B+Ck%4%eu&H5>oZQje7`OsUuYuf zuci}1+ElBZDQi@#IQvvUV+F-PLedCnRFr#G_Z)%*;w@D-q>sz@cl&#dD8H%aF^ZGs zy^p(>t4aeAVBR>c^bW;wL2PN9m5cq|m9<$uPh?xn&sfj((Yu`tQrWGOciKOFO!LZ! zTPsXviR;Cxk}Zjcf(!?o?zp_(H0_&L8jB6O>FtqY0dNMxK&G-bV}e+4u@qc?ah2%U z`cz~svZ6bbXzWaT&BgB-?NWK!Tu%@6l9gDu0FWTC92s(O^YWaDUJHzGHk*N2%3lZs zl7nRCF)DFAJ$c1Gg}Vbep@4%QgbN<%zh&6~bg+cp*`Bc$CxAfIDvBqm-P;+uborOv zk9{y%BFE9Hg0t0lXSet$&a;_u_A%D1NLXUczTXZ<*VYT3ybJ&j#z!zm&z6A8(A*eH@u5r(KTr3Q5+2E3y0rm}4t^PP#cX-nv zu2hi2XMYg3#>bTV4hNHVC(+FM>T9nVS|SmG9zPOwd{1P_X=Z}@LCsj61yHLj#8xbBhgqa zw|(!^&qSQ%o}_KcKCmzb*5&Wod-@PK&ux*Cy--@;2@g>FXV8w;wIkD#FC`huE=qumg~J)OZd;4zGkdR+ta!<*m>+-sOM|HV@Re zL_H(RoqqP$TU7QH*sSTzJ^k;8uVW+Yna@Xld0e|9(sg>L%PuqCdxebC-sk6_wr0hE z_hjE9ZCqhzWub@yeQCXUk#B^LSirWm}V2VL-d@!t;T zop169=6@Lt;M)4VO+I9XS2C>p&@9f17X2HlLoc|28g>T^F1yh2E%kUsv&xHy;QrAV zr(!)0*}(n_+0JQNBqHV*AB-~!nH9wa0z6z6K0i2|rLkOj zr)skNGL6@Ovi(se{OT|Y4+XPYf@)7$$i?vv3d1U=3j4fkJJlU8qYBBQ3W>mqZ8ZlY zzlheyXKt?0afod|;A7v(LMuk*l1Q#cKoD2DlGW%BSh5@6`^}Gz?`O>sYhV-=D=ZFd z{K#m(IQQ}ldrp9nq%9~MFwwl!C`{rMvKemrQiuPdF+iyxo59IJAOt#rfz|qlvBSk7 zJ45pY5LMMq9hw^ZPUg|po;^DHvdv9jnO-RHy|yn4Dq@JYu$Ueu=7LWlJO!Gd)ZYQp z8wRiusP6nRmgttI_@s2Cv&VO0H3t3dDMY@?UryNTw1jpjDju(pTgZpNVpw-^<<1n_ zHA2(PrFGY`HkF4lOE2%SE$Nc_ek4Vepuf}z5q*b`8*7x7dZXK}b3H&X^~Yt!kQ71@ zjnd-Gk-1`FOg^ZV-rOl`vuD+K)C|2g6eq-Y@xF8N5Qq0{E1LMz^4Hv?in0ab(%|h2 z$H2M)RpC+a$;A}t)f5X*3Kb}{%?pIzjGt&QK0U~Td?M68F9tt_Al{GQR?^!rA`6Or z|J%$|?TqWpjk6X}Kc%e^*|1%GI)$EF-HGCt6{y{Ac1He_-IDfulW##*1DepkJ@N&^ z_s8;_Up^85z+Xe`iI9$V=EehrN*Q$uMoN5&Fh_$E7vyMWI{+&jSRNd{ULj!*h|3JN zCeW)Km@QJ+@IsRfh|i!ifn7;y5jVSg{rMf- z0IxJ>XOMwb+a+}4~J{6q}}RAYE_n=SMO zIdsp3#iEye?K&dG>tE8F2Z)>gd6CC56gvPrH!}jmOb}2qcKfZ6WFz> zX?&(sX9nBC{wwKnT6B;OUj*&mklx^rLMuZ?`H@xa=7(xB{{1ooH`o~5nQ+&q;%?Wq z4cUD=fc$(tTeJMpCrD(AT7WJ9&E+U!}&&ivED zng=zsiSMPs<^dJs#f3US_}7=!Vy7zVi9*$9=Zvi)wWp^fG17TbMZ1jAC;mu+zxH3A z2yAo^OK^SL?vD=*6EL6%zq{Mo`cIGlC0QpeT<#E+@kcutCFJ^$fc>KFwWZ=l!_O3_ zFYjaZjd*_tN3HQ3QdGGY&IZDt@;_FkB&WCmD3}N~*Jr+fKJhA27~?Jk(Af zjnk?t^sCJ$X>JYwN*$a!MS&?hiUEZ1sZ}58IPAGh(CV%yla%TtC+7{{-mNtDvb}vE zF~P1;l>`5?3V|8M+1%>@XlQNr&7`N7LL4*B8~d$0%!uFi{&0GEN^{GVYszMo+uKGk z`n{;TZmOZ3G}h-ooiyjbFE*34Ee1;wA!LY9CZ#q@Nw`fb7Rr5t@N)Yn)&M&OJ&oB^t%D=R{=aJ24kxT?fK zqPkVwWuC>i#MQpd{iMRu4Wyub)jV_N5ShoxI%7f^mh%K}x6lO3qWjpsSGmfWaJ!fG zqqNCgH^jCCLb#rFDNB+((*O5tZ08fz*R0_uBJ|nqc&I=(fJ}#mP#dhkHTgfX_8eqN{WKR z(S41T6}MO&;dc^bGs$Zi`d8r=IvH7*FD`+ft=qy&TI~!WwEVSHbluY-c8@$!+wBXz zn2zZ=r(-U*-J-U3lB$TNy5$d&H5!4w;Nu1G-dbi^yAeEyr!4)d5!591#>$F^rs+uV zH>q%C-9p^U_xPRc4p^sYrx!G<6%RkbBZXi64UY>ToSJfxpyztIq^ zdDgFUiV&^*Wnl{C6NU0<-qqdg$V{8UD4aP?y8mRp<3_(o=ak?Av~Fbk4<_AQ&sp2I z)AQKVKgf+TLHho`+aXd;z;ivVgoSn2NZVb)(}*4Q@6i2j;W15Go9kyXjBr?*PQz@) z6e&Zgs1EJyRIzclS$ik?S(~?`eADu}-?N_hdU3XYWn3D-T}{!+lQeN5U**`X*4^{A z*F8YQcY|g|_I>}M>(0n#b8^18#d*Z<`D(uS5&d%&S;tgdLHaB+N^fOy5BDf_LWqQVDe?oB+z&gf(MSJKvSEz2*5_1aAPokhhpfsDc6j%&fe zY%@x1l`*2{dCO`C8G@3KMtXH=d>LT`MHTLFG<40K*7v`i=jcm?LHT>_)O`S~Mh^uN*r>AI9K>Ok57lUnRHzbaNRH}D*KNI+ zXE~qC`BFp{>dki$$4QvnKvdugenUvk^?%e@R@;`hz1G;dy7pllC!F-F>t1_N)awGA zs6e0t5SY2!LmRaA8u#!=Ig7Yk%Z}{tpZ7jfDXzbeD{2aBZ*YH-?$#tSqt*?kvWW(> zFa`*W%$#j@Z`|G=L11ryPQJ7~EpgqvicIe>DjJjqAjP~!(cWfGydgnDD~wX0yC~N= zQ1H=8dz}w5JGXwPjpa8?wvvu6&QpMMsVo@%E;ypb@6Vcc!Q2my_+YZ~x-N{7x$XEL zv4(4m@ATRCWYX;>p=&swXZ;|ysOTnt9e;egmg*zSCaVpzux``1S3|`y)1RJ2TbqSd z1xq(9tWK-tuh`AMmh)1_d)NnL-GV`Fq3XPp&-7r`Yi9Z}uNJHzdo55Iz@`K=cf~&b zpkYHy;$4%!?xKrSN>vv?1LGV-O#54-lchhY!~^dvVzvN!VZeKr|5ed>->v1^Il>eS z$pAydN;83rtLoT>rR1|kR)5YVSaO4LrjnjP)VQiEP&8xc3C3NqL);)Hh&ouQ6?;Ph zpC4N*7&2aI;+K^?jgTj?3N!pyI&Y%4F>&p0&7JkTt4^*Fa24J>Pg6B$fi1WQA*;OD zG5*4UGdryrm8p<=m@Tuql7GtYCAt2uxl_S$%S8f#lp|+OK&+z0XaD+t^EConTx-V@ zCMJ?YiJ}kkUb9gnCn*RFycMFFV1?GdZHS%lfJCTGbu`PL$BWjUjSqc80c)4j=4Ll9nI(0=kaR{1@)G;H z#s`sQ`9jiTy~1vE?-7P9VRdjXrFr92|H?@WX&Lc#M))-4;~ma&jJ2#2{8_ckvCi#` zzHx#)@i8bJ?SNbGmz9M+!~;8y{(}x!1#UMcgpQ6d#v=6LRs(IVmsSG zF>~*CkCSdLWt0eNnEi43_0%8pO0Ycz&8wm>J|Px#jlXbgaKCid=#^RTz79w3 zz76%p^`f+vTe)Id){*C2<9BG;44mPo&{tRAU4uEbCd0t9Q5IDOKYe$?hCY;=BttL? z6F)7}e-=X>5sKu&7M^a%piVaz{To4yJ@*CVBWu5V&QFgH%~662Hj&C$dU1oyUf~8G zawmVTW!zw1FnsE7t#ZlSc&+-z(pfo=l#o+c;}!26aDjhqrWQ-@tiw_;taZog zi*}!VzGFhnbnl%WA=)LHH^Ig@I}-F|+KVkpBYjKT&QcxvX6-XK21%QgEuCSJj*^KM z#@!%^H+s|3o@DKAKz2md~ZV>)s zL~39Tfv-0G2?!jTY@{8i3;(Wf-w>a5@;)dS*5aNY@^h5)?eQurNsCH%-CtLjeeYr2 zvDN9rC2BUTuVg#={&T|of5lU+X!I5x|8o9wuR0coXn#-wA_~!%6=RkM-4K{rwdv<^ z;aVqaj20TDm$MJ9R4S?@5FlFj`n#3tUEKT_uy^}*z$;iT!Q*!KBD3A7Qrq+0nfvf!v-HeS|! zZQ@&hO#06i3~zcA$IRzPeC>*F&wPH9GGVG{S1&hV!$cKjYw2U(`#q}^KAN#g{-63! zI=-gvr5>Z`l!H}*_Ajv<-Vu~&+^lPagk}d`bW4bk)iDC3hR#jAsn;-j`OT8(|0K;e zW7s4JUVX{Vn{ohX29TB<{$TRmCvF4j!O-zLcRO!~s38ed@M2Of8RTSTiBt(9feLNu z3W5lH`PL?O41alv>UxE~BTK>}M7}_@bkGNrO_b-0ZK5?V)0M+Usb5uvJ$SEkE719= z^j6&1h@RuYcBPuR{dPl381Q6z%k!qW8{I%6()V%v;nkzq);Zw$$KCq6n%9s&nh9J- zgp31BYzU~k4`1}8vc^b&wFl-&2*GNv=uh1!!eiFm)Ou~ZTLHEeKv8sw)6x1 zJAD|xRHmmjmh0|}u#oiCO~E0J5^OkW_CCv=U*v+&EtZS=Lr0)*Eoo=cy6Sm-{WAP6DYD^!4Fpy7v9a~&mY33Zd7{t%MJKxD%kIR8X@m-!T7blFpE9cm{ zJ;Uv3YI!|d$>#3)nU(y$;m&kq>geoekG*K6;Yvv==t{!BOz+PVhBXG|n`2XmpA|&! z1H&A#ma7DS%CvcB2XvPYIJ}rK7#6-9Urep>AV?Xv7vC!M2~F`PhJ={oHyS;+em=gu z#E_X!af&us&SuB(A&MvMyd=+HqEp=YH6-gJpo4M|vBK*i zKZBjZo>g6w<<{oPIiei~b4dCV?w+dOD<6VeS4P>HQpRe($C!_FTOVLnqjy2eMU}Z% zC%VOlJSBPNaW44W^S^xx?#zVG%!y%9RF7HoTt0EV{BW_mwvu#+blyjo#&Zwyx>