mirror of https://github.com/axmolengine/axmol.git
merge cocos resolve conflict
This commit is contained in:
commit
5274b4f958
3
AUTHORS
3
AUTHORS
|
@ -997,6 +997,9 @@ Developers:
|
|||
|
||||
jagd
|
||||
Added setSubsteps() and getSubsteps() in PhysicsWorld
|
||||
|
||||
denpen
|
||||
Fixed a bug that scroll view hidden picks up the touch events.
|
||||
|
||||
Retired Core Developers:
|
||||
WenSheng Yang
|
||||
|
|
|
@ -1,5 +1,6 @@
|
|||
cocos2d-x-3.3?? ??
|
||||
[NEW] ActionManager: added removeAllActionsByTag()
|
||||
[NEW] Audio: added new audio system for iOS and Android
|
||||
[NEW] GLViewProtocol: added getAllTouches()
|
||||
[NEW] Node: added stopAllActionsByTag()
|
||||
[NEW] PhysicsWorld: add setSubsteps() and getSubsteps()
|
||||
|
@ -13,6 +14,7 @@ cocos2d-x-3.3?? ??
|
|||
[FIX] Node: create unneeded temple `Vec2` object in `setPosition(int, int)`, `setPositionX()` and `setPositionY()`
|
||||
[FIX] Node: skew effect is wrong
|
||||
[FIX] Node: setNormalizedPosition can not take effect if parent position is not changed
|
||||
[FIX] External: ScrollView: scroll view hidden picks up the touch events
|
||||
[FIX] TextureAtlas: may crash if only drawing part of it
|
||||
|
||||
cocos2d-x-3.3alpha0 Aug.28 2014
|
||||
|
|
|
@ -24,7 +24,7 @@
|
|||
# ****************************************************************************/
|
||||
|
||||
cmake_minimum_required(VERSION 2.8)
|
||||
project (Cocos2dx)
|
||||
project (Cocos2d-X)
|
||||
|
||||
# The version number
|
||||
set(COCOS2D_X_VERSION 3.3.0)
|
||||
|
|
|
@ -1267,6 +1267,14 @@
|
|||
299CF1FC19A434BC00C378C1 /* ccRandom.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 299CF1F919A434BC00C378C1 /* ccRandom.cpp */; };
|
||||
299CF1FD19A434BC00C378C1 /* ccRandom.h in Headers */ = {isa = PBXBuildFile; fileRef = 299CF1FA19A434BC00C378C1 /* ccRandom.h */; };
|
||||
299CF1FE19A434BC00C378C1 /* ccRandom.h in Headers */ = {isa = PBXBuildFile; fileRef = 299CF1FA19A434BC00C378C1 /* ccRandom.h */; };
|
||||
3E2BDADE19C030ED0055CDCD /* AudioEngine.h in Headers */ = {isa = PBXBuildFile; fileRef = 3E2BDADD19C030ED0055CDCD /* AudioEngine.h */; };
|
||||
3E2BDAE519C0329B0055CDCD /* AudioCache.h in Headers */ = {isa = PBXBuildFile; fileRef = 3E2BDADF19C0329B0055CDCD /* AudioCache.h */; };
|
||||
3E2BDAE619C0329B0055CDCD /* AudioCache.mm in Sources */ = {isa = PBXBuildFile; fileRef = 3E2BDAE019C0329B0055CDCD /* AudioCache.mm */; };
|
||||
3E2BDAE719C0329B0055CDCD /* AudioEngine-inl.h in Headers */ = {isa = PBXBuildFile; fileRef = 3E2BDAE119C0329B0055CDCD /* AudioEngine-inl.h */; };
|
||||
3E2BDAE819C0329B0055CDCD /* AudioEngine-inl.mm in Sources */ = {isa = PBXBuildFile; fileRef = 3E2BDAE219C0329B0055CDCD /* AudioEngine-inl.mm */; };
|
||||
3E2BDAE919C0329B0055CDCD /* AudioPlayer.h in Headers */ = {isa = PBXBuildFile; fileRef = 3E2BDAE319C0329B0055CDCD /* AudioPlayer.h */; };
|
||||
3E2BDAEA19C0329B0055CDCD /* AudioPlayer.mm in Sources */ = {isa = PBXBuildFile; fileRef = 3E2BDAE419C0329B0055CDCD /* AudioPlayer.mm */; };
|
||||
3E2BDAEC19C0436F0055CDCD /* AudioEngine.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 3E2BDAEB19C0436F0055CDCD /* AudioEngine.cpp */; };
|
||||
3E6176681960F89B00DE83F5 /* CCController-iOS.mm in Sources */ = {isa = PBXBuildFile; fileRef = 3E6176551960F89B00DE83F5 /* CCController-iOS.mm */; };
|
||||
3E6176691960F89B00DE83F5 /* CCController.h in Headers */ = {isa = PBXBuildFile; fileRef = 3E6176561960F89B00DE83F5 /* CCController.h */; };
|
||||
3E6176741960F89B00DE83F5 /* CCEventController.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 3E6176611960F89B00DE83F5 /* CCEventController.cpp */; };
|
||||
|
@ -2282,6 +2290,14 @@
|
|||
37936A3C1869B76800E974DD /* reader.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = reader.h; sourceTree = "<group>"; };
|
||||
37936A3D1869B76800E974DD /* stringbuffer.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = stringbuffer.h; sourceTree = "<group>"; };
|
||||
37936A3E1869B76800E974DD /* writer.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = writer.h; sourceTree = "<group>"; };
|
||||
3E2BDADD19C030ED0055CDCD /* AudioEngine.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = AudioEngine.h; sourceTree = "<group>"; };
|
||||
3E2BDADF19C0329B0055CDCD /* AudioCache.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = AudioCache.h; sourceTree = "<group>"; };
|
||||
3E2BDAE019C0329B0055CDCD /* AudioCache.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = AudioCache.mm; sourceTree = "<group>"; };
|
||||
3E2BDAE119C0329B0055CDCD /* AudioEngine-inl.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = "AudioEngine-inl.h"; sourceTree = "<group>"; };
|
||||
3E2BDAE219C0329B0055CDCD /* AudioEngine-inl.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = "AudioEngine-inl.mm"; sourceTree = "<group>"; };
|
||||
3E2BDAE319C0329B0055CDCD /* AudioPlayer.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = AudioPlayer.h; sourceTree = "<group>"; };
|
||||
3E2BDAE419C0329B0055CDCD /* AudioPlayer.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = AudioPlayer.mm; sourceTree = "<group>"; };
|
||||
3E2BDAEB19C0436F0055CDCD /* AudioEngine.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = AudioEngine.cpp; sourceTree = "<group>"; };
|
||||
3E6176551960F89B00DE83F5 /* CCController-iOS.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; name = "CCController-iOS.mm"; path = "../base/CCController-iOS.mm"; sourceTree = "<group>"; };
|
||||
3E6176561960F89B00DE83F5 /* CCController.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = CCController.h; path = ../base/CCController.h; sourceTree = "<group>"; };
|
||||
3E6176611960F89B00DE83F5 /* CCEventController.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = CCEventController.cpp; path = ../base/CCEventController.cpp; sourceTree = "<group>"; };
|
||||
|
@ -3996,6 +4012,7 @@
|
|||
46A15FD01807A56F005B8026 /* audio */ = {
|
||||
isa = PBXGroup;
|
||||
children = (
|
||||
3E2BDAEB19C0436F0055CDCD /* AudioEngine.cpp */,
|
||||
46A15FE01807A56F005B8026 /* include */,
|
||||
46A15FE31807A56F005B8026 /* ios */,
|
||||
46A15FF31807A56F005B8026 /* mac */,
|
||||
|
@ -4007,6 +4024,7 @@
|
|||
46A15FE01807A56F005B8026 /* include */ = {
|
||||
isa = PBXGroup;
|
||||
children = (
|
||||
3E2BDADD19C030ED0055CDCD /* AudioEngine.h */,
|
||||
46A15FE11807A56F005B8026 /* Export.h */,
|
||||
46A15FE21807A56F005B8026 /* SimpleAudioEngine.h */,
|
||||
);
|
||||
|
@ -4016,6 +4034,12 @@
|
|||
46A15FE31807A56F005B8026 /* ios */ = {
|
||||
isa = PBXGroup;
|
||||
children = (
|
||||
3E2BDADF19C0329B0055CDCD /* AudioCache.h */,
|
||||
3E2BDAE019C0329B0055CDCD /* AudioCache.mm */,
|
||||
3E2BDAE119C0329B0055CDCD /* AudioEngine-inl.h */,
|
||||
3E2BDAE219C0329B0055CDCD /* AudioEngine-inl.mm */,
|
||||
3E2BDAE319C0329B0055CDCD /* AudioPlayer.h */,
|
||||
3E2BDAE419C0329B0055CDCD /* AudioPlayer.mm */,
|
||||
46A15FE41807A56F005B8026 /* CDAudioManager.h */,
|
||||
46A15FE51807A56F005B8026 /* CDAudioManager.m */,
|
||||
46A15FE61807A56F005B8026 /* CDConfig.h */,
|
||||
|
@ -5377,6 +5401,7 @@
|
|||
1A5701A0180BCB590088DEC7 /* CCFont.h in Headers */,
|
||||
292DB14819B4574100A80320 /* UIEditBoxImpl-ios.h in Headers */,
|
||||
15AE1A0819AAD3A700C27E9E /* BoneData.h in Headers */,
|
||||
3E2BDADE19C030ED0055CDCD /* AudioEngine.h in Headers */,
|
||||
50ABBD9A1925AB4100A911A9 /* CCGLProgramStateCache.h in Headers */,
|
||||
15AE181D19AAD2F700C27E9E /* CCBundle3D.h in Headers */,
|
||||
15AE192519AAD35100C27E9E /* CocoLoader.h in Headers */,
|
||||
|
@ -5430,6 +5455,7 @@
|
|||
5034CA22191D591100CE6051 /* ccShader_PositionTextureColorAlphaTest.frag in Headers */,
|
||||
15AE1B8E19AADA9A00C27E9E /* UIDeprecated.h in Headers */,
|
||||
15AE1A3919AAD3D500C27E9E /* Box2D.h in Headers */,
|
||||
3E2BDAE519C0329B0055CDCD /* AudioCache.h in Headers */,
|
||||
50ABBECE1925AB6F00A911A9 /* s3tc.h in Headers */,
|
||||
50643BE519BFCF1800EF68ED /* CCPlatformMacros.h in Headers */,
|
||||
15AE1BFA19AAE01E00C27E9E /* CCControlSwitch.h in Headers */,
|
||||
|
@ -5523,6 +5549,7 @@
|
|||
15AE1BAE19AADFDF00C27E9E /* UILayoutParameter.h in Headers */,
|
||||
15AE18C819AAD33D00C27E9E /* CCMenuItemImageLoader.h in Headers */,
|
||||
15AE18D119AAD33D00C27E9E /* CCNodeLoaderLibrary.h in Headers */,
|
||||
3E2BDAE719C0329B0055CDCD /* AudioEngine-inl.h in Headers */,
|
||||
15AE1AC319AAD40300C27E9E /* b2DistanceJoint.h in Headers */,
|
||||
50ABBE741925AB6F00A911A9 /* CCEventListenerMouse.h in Headers */,
|
||||
1A5702CB180BCE370088DEC7 /* CCTextFieldTTF.h in Headers */,
|
||||
|
@ -5556,6 +5583,7 @@
|
|||
B375107F1823ACA100B3BA6A /* CCPhysicsContactInfo_chipmunk.h in Headers */,
|
||||
15AE180719AAD2F700C27E9E /* 3dExport.h in Headers */,
|
||||
15AE1A2019AAD3A700C27E9E /* spine-cocos2dx.h in Headers */,
|
||||
3E2BDAE919C0329B0055CDCD /* AudioPlayer.h in Headers */,
|
||||
15AE185D19AAD31200C27E9E /* CocosDenshion.h in Headers */,
|
||||
15AE194319AAD35100C27E9E /* CCColliderDetector.h in Headers */,
|
||||
15AE1BC419AADFFB00C27E9E /* ExtensionMacros.h in Headers */,
|
||||
|
@ -5759,7 +5787,7 @@
|
|||
1551A336158F2AB200E66CFE /* Project object */ = {
|
||||
isa = PBXProject;
|
||||
attributes = {
|
||||
LastUpgradeCheck = 0500;
|
||||
LastUpgradeCheck = 0600;
|
||||
ORGANIZATIONNAME = "";
|
||||
};
|
||||
buildConfigurationList = 1551A339158F2AB200E66CFE /* Build configuration list for PBXProject "cocos2d_libs" */;
|
||||
|
@ -6213,6 +6241,7 @@
|
|||
50ABBDA01925AB4100A911A9 /* CCGroupCommand.cpp in Sources */,
|
||||
46A171031807CECB005B8026 /* CCPhysicsShape.cpp in Sources */,
|
||||
50ABC0161926664800A911A9 /* CCImage.cpp in Sources */,
|
||||
3E2BDAE819C0329B0055CDCD /* AudioEngine-inl.mm in Sources */,
|
||||
1A01C6A518F58F7500EFE3A6 /* CCNotificationCenter.cpp in Sources */,
|
||||
292DB14E19B4574100A80320 /* UIEditBoxImpl-mac.mm in Sources */,
|
||||
15AE1BFB19AAE01E00C27E9E /* CCControlUtils.cpp in Sources */,
|
||||
|
@ -6241,6 +6270,7 @@
|
|||
B257B44F1989D5E800D9A687 /* CCPrimitive.cpp in Sources */,
|
||||
50ABBE281925AB6F00A911A9 /* CCAutoreleasePool.cpp in Sources */,
|
||||
15AE18D519AAD33D00C27E9E /* CCScale9SpriteLoader.cpp in Sources */,
|
||||
3E2BDAEA19C0329B0055CDCD /* AudioPlayer.mm in Sources */,
|
||||
15AE192919AAD35100C27E9E /* TriggerMng.cpp in Sources */,
|
||||
15AE185E19AAD31200C27E9E /* CocosDenshion.m in Sources */,
|
||||
46A170FE1807CECB005B8026 /* CCPhysicsContact.cpp in Sources */,
|
||||
|
@ -6558,6 +6588,7 @@
|
|||
3E6176761960F89B00DE83F5 /* CCEventListenerController.cpp in Sources */,
|
||||
15AE1AC219AAD40300C27E9E /* b2DistanceJoint.cpp in Sources */,
|
||||
503DD8E71926736A00CD74DD /* CCEAGLView-ios.mm in Sources */,
|
||||
3E2BDAEC19C0436F0055CDCD /* AudioEngine.cpp in Sources */,
|
||||
50ABBDA41925AB4100A911A9 /* CCQuadCommand.cpp in Sources */,
|
||||
15AE18C319AAD33D00C27E9E /* CCLayerGradientLoader.cpp in Sources */,
|
||||
15AE197919AAD35700C27E9E /* CCActionTimelineCache.cpp in Sources */,
|
||||
|
@ -6584,6 +6615,7 @@
|
|||
15AE18CC19AAD33D00C27E9E /* CCNode+CCBRelativePositioning.cpp in Sources */,
|
||||
50ABBD5D1925AB0000A911A9 /* Vec3.cpp in Sources */,
|
||||
50ABC0121926664800A911A9 /* CCGLView.cpp in Sources */,
|
||||
3E2BDAE619C0329B0055CDCD /* AudioCache.mm in Sources */,
|
||||
50ABC0021926664800A911A9 /* CCLock-apple.cpp in Sources */,
|
||||
50ABBEBC1925AB6F00A911A9 /* ccUtils.cpp in Sources */,
|
||||
15AE1A4719AAD3D500C27E9E /* b2ChainShape.cpp in Sources */,
|
||||
|
@ -6622,7 +6654,6 @@
|
|||
isa = XCBuildConfiguration;
|
||||
buildSettings = {
|
||||
ALWAYS_SEARCH_USER_PATHS = YES;
|
||||
ARCHS = "$(ARCHS_STANDARD_32_64_BIT)";
|
||||
CLANG_CXX_LANGUAGE_STANDARD = "c++0x";
|
||||
CLANG_CXX_LIBRARY = "libc++";
|
||||
CLANG_WARN_BOOL_CONVERSION = YES;
|
||||
|
@ -6660,7 +6691,6 @@
|
|||
isa = XCBuildConfiguration;
|
||||
buildSettings = {
|
||||
ALWAYS_SEARCH_USER_PATHS = YES;
|
||||
ARCHS = "$(ARCHS_STANDARD_32_64_BIT)";
|
||||
CLANG_CXX_LANGUAGE_STANDARD = "c++0x";
|
||||
CLANG_CXX_LIBRARY = "libc++";
|
||||
CLANG_WARN_BOOL_CONVERSION = YES;
|
||||
|
@ -6695,7 +6725,7 @@
|
|||
isa = XCBuildConfiguration;
|
||||
buildSettings = {
|
||||
ALWAYS_SEARCH_USER_PATHS = YES;
|
||||
ARCHS = "$(ARCHS_STANDARD)";
|
||||
COMBINE_HIDPI_IMAGES = YES;
|
||||
EXECUTABLE_EXTENSION = a;
|
||||
EXECUTABLE_PREFIX = "";
|
||||
GCC_PRECOMPILE_PREFIX_HEADER = YES;
|
||||
|
@ -6729,7 +6759,7 @@
|
|||
isa = XCBuildConfiguration;
|
||||
buildSettings = {
|
||||
ALWAYS_SEARCH_USER_PATHS = YES;
|
||||
ARCHS = "$(ARCHS_STANDARD)";
|
||||
COMBINE_HIDPI_IMAGES = YES;
|
||||
EXECUTABLE_EXTENSION = a;
|
||||
EXECUTABLE_PREFIX = "";
|
||||
GCC_GENERATE_DEBUGGING_SYMBOLS = NO;
|
||||
|
@ -6764,7 +6794,6 @@
|
|||
isa = XCBuildConfiguration;
|
||||
buildSettings = {
|
||||
ALWAYS_SEARCH_USER_PATHS = YES;
|
||||
ARCHS = "$(ARCHS_STANDARD)";
|
||||
EXECUTABLE_PREFIX = "";
|
||||
GCC_PRECOMPILE_PREFIX_HEADER = YES;
|
||||
GCC_PREFIX_HEADER = "../cocos/cocos2d-prefix.pch";
|
||||
|
@ -6796,7 +6825,6 @@
|
|||
isa = XCBuildConfiguration;
|
||||
buildSettings = {
|
||||
ALWAYS_SEARCH_USER_PATHS = YES;
|
||||
ARCHS = "$(ARCHS_STANDARD)";
|
||||
EXECUTABLE_PREFIX = "";
|
||||
GCC_GENERATE_DEBUGGING_SYMBOLS = NO;
|
||||
GCC_PRECOMPILE_PREFIX_HEADER = YES;
|
||||
|
|
|
@ -871,6 +871,8 @@
|
|||
38FA2E74194AEBE100FF2BE4 /* ActionTimelineTestScene.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 38FA2E71194AEBE100FF2BE4 /* ActionTimelineTestScene.cpp */; };
|
||||
38FA2E76194AECF800FF2BE4 /* ActionTimeline in Resources */ = {isa = PBXBuildFile; fileRef = 38FA2E75194AECF800FF2BE4 /* ActionTimeline */; };
|
||||
38FA2E77194AECF800FF2BE4 /* ActionTimeline in Resources */ = {isa = PBXBuildFile; fileRef = 38FA2E75194AECF800FF2BE4 /* ActionTimeline */; };
|
||||
3E2BDAD019BEA3410055CDCD /* NewAudioEngineTest.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 3E2BDACE19BEA3410055CDCD /* NewAudioEngineTest.cpp */; };
|
||||
3E2BDAD219BEA3E20055CDCD /* audio in Resources */ = {isa = PBXBuildFile; fileRef = 3E2BDAD119BEA3E20055CDCD /* audio */; };
|
||||
3E6177221960FAED00DE83F5 /* libcocos2d iOS.a in Frameworks */ = {isa = PBXBuildFile; fileRef = 46A15FBE1807A4F9005B8026 /* libcocos2d iOS.a */; };
|
||||
3E6177241960FAED00DE83F5 /* CoreMotion.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = D60AE43317F7FFE100757E4B /* CoreMotion.framework */; };
|
||||
3E6177251960FAED00DE83F5 /* libz.dylib in Frameworks */ = {isa = PBXBuildFile; fileRef = 15C6482E165F399D007D4F18 /* libz.dylib */; };
|
||||
|
@ -931,8 +933,8 @@
|
|||
A07A52C31783B02C0073F6A7 /* AVFoundation.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = A07A52C11783B01F0073F6A7 /* AVFoundation.framework */; };
|
||||
B2507B6B192589AF00FA4972 /* Shaders3D in Resources */ = {isa = PBXBuildFile; fileRef = B2507B6A192589AF00FA4972 /* Shaders3D */; };
|
||||
B2507B6C192589AF00FA4972 /* Shaders3D in Resources */ = {isa = PBXBuildFile; fileRef = B2507B6A192589AF00FA4972 /* Shaders3D */; };
|
||||
B60EF5F919B842B000EAF38D /* BillBoardTest.cpp in Sources */ = {isa = PBXBuildFile; fileRef = B60EF5F719B842B000EAF38D /* BillBoardTest.cpp */; };
|
||||
B60EF5FA19B842B000EAF38D /* BillBoardTest.cpp in Sources */ = {isa = PBXBuildFile; fileRef = B60EF5F719B842B000EAF38D /* BillBoardTest.cpp */; };
|
||||
B609E67319C18DAD003D0074 /* BillBoardTest.cpp in Sources */ = {isa = PBXBuildFile; fileRef = B609E67119C18DAD003D0074 /* BillBoardTest.cpp */; };
|
||||
B609E67419C18DAD003D0074 /* BillBoardTest.cpp in Sources */ = {isa = PBXBuildFile; fileRef = B609E67119C18DAD003D0074 /* BillBoardTest.cpp */; };
|
||||
C04F935A1941B05400E9FEAB /* TileMapTest2.cpp in Sources */ = {isa = PBXBuildFile; fileRef = C04F93581941B05400E9FEAB /* TileMapTest2.cpp */; };
|
||||
C04F935B1941B05400E9FEAB /* TileMapTest2.cpp in Sources */ = {isa = PBXBuildFile; fileRef = C04F93581941B05400E9FEAB /* TileMapTest2.cpp */; };
|
||||
C08689C118D370C90093E810 /* background.caf in Resources */ = {isa = PBXBuildFile; fileRef = C08689C018D370C90093E810 /* background.caf */; };
|
||||
|
@ -2894,6 +2896,9 @@
|
|||
38FA2E71194AEBE100FF2BE4 /* ActionTimelineTestScene.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = ActionTimelineTestScene.cpp; sourceTree = "<group>"; };
|
||||
38FA2E72194AEBE100FF2BE4 /* ActionTimelineTestScene.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = ActionTimelineTestScene.h; sourceTree = "<group>"; };
|
||||
38FA2E75194AECF800FF2BE4 /* ActionTimeline */ = {isa = PBXFileReference; lastKnownFileType = folder; name = ActionTimeline; path = "../tests/cpp-tests/Resources/ActionTimeline"; sourceTree = "<group>"; };
|
||||
3E2BDACE19BEA3410055CDCD /* NewAudioEngineTest.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = NewAudioEngineTest.cpp; sourceTree = "<group>"; };
|
||||
3E2BDACF19BEA3410055CDCD /* NewAudioEngineTest.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = NewAudioEngineTest.h; sourceTree = "<group>"; };
|
||||
3E2BDAD119BEA3E20055CDCD /* audio */ = {isa = PBXFileReference; lastKnownFileType = folder; name = audio; path = "../tests/cpp-tests/Resources/audio"; sourceTree = "<group>"; };
|
||||
3E6176B71960FA6300DE83F5 /* AppDelegate.cpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; path = AppDelegate.cpp; sourceTree = "<group>"; };
|
||||
3E6176B81960FA6300DE83F5 /* AppDelegate.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = AppDelegate.h; sourceTree = "<group>"; };
|
||||
3E6176B91960FA6300DE83F5 /* AppMacros.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = AppMacros.h; sourceTree = "<group>"; };
|
||||
|
@ -2950,8 +2955,8 @@
|
|||
A07A52BB1783AEB80073F6A7 /* CoreGraphics.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = CoreGraphics.framework; path = Platforms/iPhoneOS.platform/Developer/SDKs/iPhoneOS6.1.sdk/System/Library/Frameworks/CoreGraphics.framework; sourceTree = DEVELOPER_DIR; };
|
||||
A07A52C11783B01F0073F6A7 /* AVFoundation.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = AVFoundation.framework; path = Platforms/iPhoneOS.platform/Developer/SDKs/iPhoneOS6.1.sdk/System/Library/Frameworks/AVFoundation.framework; sourceTree = DEVELOPER_DIR; };
|
||||
B2507B6A192589AF00FA4972 /* Shaders3D */ = {isa = PBXFileReference; lastKnownFileType = folder; name = Shaders3D; path = "../tests/cpp-tests/Resources/Shaders3D"; sourceTree = "<group>"; };
|
||||
B60EF5F719B842B000EAF38D /* BillBoardTest.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = BillBoardTest.cpp; path = BillBoardTest/BillBoardTest.cpp; sourceTree = "<group>"; };
|
||||
B60EF5F819B842B000EAF38D /* BillBoardTest.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = BillBoardTest.h; path = BillBoardTest/BillBoardTest.h; sourceTree = "<group>"; };
|
||||
B609E67119C18DAD003D0074 /* BillBoardTest.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = BillBoardTest.cpp; path = BillBoardTest/BillBoardTest.cpp; sourceTree = "<group>"; };
|
||||
B609E67219C18DAD003D0074 /* BillBoardTest.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = BillBoardTest.h; path = BillBoardTest/BillBoardTest.h; sourceTree = "<group>"; };
|
||||
C04F93581941B05400E9FEAB /* TileMapTest2.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = TileMapTest2.cpp; sourceTree = "<group>"; };
|
||||
C04F93591941B05400E9FEAB /* TileMapTest2.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = TileMapTest2.h; sourceTree = "<group>"; };
|
||||
C08689C018D370C90093E810 /* background.caf */ = {isa = PBXFileReference; lastKnownFileType = file; name = background.caf; path = "../tests/cpp-tests/Resources/background.caf"; sourceTree = "<group>"; };
|
||||
|
@ -5426,7 +5431,8 @@
|
|||
1AC3592418CECF0A00F37B72 /* Classes */ = {
|
||||
isa = PBXGroup;
|
||||
children = (
|
||||
B60EF5F619B8428700EAF38D /* BillBoardTest */,
|
||||
B609E67019C18D90003D0074 /* BillBoardTest */,
|
||||
3E2BDACD19BEA3410055CDCD /* NewAudioEngineTest */,
|
||||
3E9E75CB199324A8005B7047 /* Camera3DTest */,
|
||||
1AC3592818CECF0A00F37B72 /* ActionManagerTest */,
|
||||
1AC3592B18CECF0A00F37B72 /* ActionsEaseTest */,
|
||||
|
@ -6450,6 +6456,7 @@
|
|||
1AC35CA818CED83500F37B72 /* Resources */ = {
|
||||
isa = PBXGroup;
|
||||
children = (
|
||||
3E2BDAD119BEA3E20055CDCD /* audio */,
|
||||
38FA2E75194AECF800FF2BE4 /* ActionTimeline */,
|
||||
B2507B6A192589AF00FA4972 /* Shaders3D */,
|
||||
3E92EA841921A7720094CD21 /* Sprite3DTest */,
|
||||
|
@ -7031,6 +7038,15 @@
|
|||
path = CocoStudioActionTimelineTest;
|
||||
sourceTree = "<group>";
|
||||
};
|
||||
3E2BDACD19BEA3410055CDCD /* NewAudioEngineTest */ = {
|
||||
isa = PBXGroup;
|
||||
children = (
|
||||
3E2BDACE19BEA3410055CDCD /* NewAudioEngineTest.cpp */,
|
||||
3E2BDACF19BEA3410055CDCD /* NewAudioEngineTest.h */,
|
||||
);
|
||||
path = NewAudioEngineTest;
|
||||
sourceTree = "<group>";
|
||||
};
|
||||
3E6176B51960FA6300DE83F5 /* game-controller-test */ = {
|
||||
isa = PBXGroup;
|
||||
children = (
|
||||
|
@ -7130,11 +7146,11 @@
|
|||
name = Products;
|
||||
sourceTree = "<group>";
|
||||
};
|
||||
B60EF5F619B8428700EAF38D /* BillBoardTest */ = {
|
||||
B609E67019C18D90003D0074 /* BillBoardTest */ = {
|
||||
isa = PBXGroup;
|
||||
children = (
|
||||
B60EF5F719B842B000EAF38D /* BillBoardTest.cpp */,
|
||||
B60EF5F819B842B000EAF38D /* BillBoardTest.h */,
|
||||
B609E67119C18DAD003D0074 /* BillBoardTest.cpp */,
|
||||
B609E67219C18DAD003D0074 /* BillBoardTest.h */,
|
||||
);
|
||||
name = BillBoardTest;
|
||||
sourceTree = "<group>";
|
||||
|
@ -7333,7 +7349,7 @@
|
|||
29B97313FDCFA39411CA2CEA /* Project object */ = {
|
||||
isa = PBXProject;
|
||||
attributes = {
|
||||
LastUpgradeCheck = 0510;
|
||||
LastUpgradeCheck = 0600;
|
||||
};
|
||||
buildConfigurationList = C01FCF4E08A954540054247B /* Build configuration list for PBXProject "cocos2d_tests" */;
|
||||
compatibilityVersion = "Xcode 3.2";
|
||||
|
@ -7828,6 +7844,7 @@
|
|||
1AC35CD518CED84500F37B72 /* ccb in Resources */,
|
||||
1AC35CE118CED84500F37B72 /* configs in Resources */,
|
||||
1AC35CE918CED84500F37B72 /* extensions in Resources */,
|
||||
3E2BDAD219BEA3E20055CDCD /* audio in Resources */,
|
||||
C08689C318D370C90093E810 /* background.caf in Resources */,
|
||||
1AC35C9518CECF1400F37B72 /* Icon-72.png in Resources */,
|
||||
1AC35D0B18CED84500F37B72 /* zwoptex in Resources */,
|
||||
|
@ -8030,7 +8047,7 @@
|
|||
1AC35B7D18CECF0C00F37B72 /* PlayerController.cpp in Sources */,
|
||||
29080D9F191B595E0066F8DF /* CustomReader.cpp in Sources */,
|
||||
1AC35BE718CECF0C00F37B72 /* CCControlScene.cpp in Sources */,
|
||||
B60EF5F919B842B000EAF38D /* BillBoardTest.cpp in Sources */,
|
||||
B609E67319C18DAD003D0074 /* BillBoardTest.cpp in Sources */,
|
||||
292CF01419A1965E00E8E6A0 /* UIEditBoxTest.cpp in Sources */,
|
||||
29080DBF191B595E0066F8DF /* UIPageViewTest_Editor.cpp in Sources */,
|
||||
1AC35B5F18CECF0C00F37B72 /* DataVisitorTest.cpp in Sources */,
|
||||
|
@ -8215,10 +8232,12 @@
|
|||
292CF01519A1965E00E8E6A0 /* UIEditBoxTest.cpp in Sources */,
|
||||
1AC35B2818CECF0C00F37B72 /* ActionsTest.cpp in Sources */,
|
||||
1AC35C4A18CECF0C00F37B72 /* ShaderTest.cpp in Sources */,
|
||||
B609E67419C18DAD003D0074 /* BillBoardTest.cpp in Sources */,
|
||||
C04F935B1941B05400E9FEAB /* TileMapTest2.cpp in Sources */,
|
||||
1AC35B4418CECF0C00F37B72 /* Bug-624.cpp in Sources */,
|
||||
1AC35BF818CECF0C00F37B72 /* SocketIOTest.cpp in Sources */,
|
||||
1AC35C5018CECF0C00F37B72 /* SpriteTest.cpp in Sources */,
|
||||
3E2BDAD019BEA3410055CDCD /* NewAudioEngineTest.cpp in Sources */,
|
||||
1AC35C0418CECF0C00F37B72 /* FileUtilsTest.cpp in Sources */,
|
||||
1AC35B5C18CECF0C00F37B72 /* CurlTest.cpp in Sources */,
|
||||
1AC35C0018CECF0C00F37B72 /* CustomTableViewCell.cpp in Sources */,
|
||||
|
@ -8255,7 +8274,6 @@
|
|||
1AC35BEE18CECF0C00F37B72 /* CCControlStepperTest.cpp in Sources */,
|
||||
1AC35C3418CECF0C00F37B72 /* PerformanceScenarioTest.cpp in Sources */,
|
||||
29080DA4191B595E0066F8DF /* UIButtonTest.cpp in Sources */,
|
||||
B60EF5FA19B842B000EAF38D /* BillBoardTest.cpp in Sources */,
|
||||
1AC35C5A18CECF0C00F37B72 /* TextureAtlasEncryptionTest.cpp in Sources */,
|
||||
1AC35B5618CECF0C00F37B72 /* ConfigurationTest.cpp in Sources */,
|
||||
1AC35BE618CECF0C00F37B72 /* CCControlPotentiometerTest.cpp in Sources */,
|
||||
|
@ -8573,7 +8591,6 @@
|
|||
1A0EE2B018CDF6DA004CD58F /* Debug */ = {
|
||||
isa = XCBuildConfiguration;
|
||||
buildSettings = {
|
||||
ARCHS = "$(ARCHS_STANDARD)";
|
||||
GCC_PRECOMPILE_PREFIX_HEADER = YES;
|
||||
GCC_PREPROCESSOR_DEFINITIONS = (
|
||||
"$(inherited)",
|
||||
|
@ -8588,7 +8605,6 @@
|
|||
1A0EE2B118CDF6DA004CD58F /* Release */ = {
|
||||
isa = XCBuildConfiguration;
|
||||
buildSettings = {
|
||||
ARCHS = "$(ARCHS_STANDARD)";
|
||||
GCC_PRECOMPILE_PREFIX_HEADER = YES;
|
||||
GCC_PREPROCESSOR_DEFINITIONS = (
|
||||
"$(inherited)",
|
||||
|
@ -8604,7 +8620,6 @@
|
|||
1A0EE31218CDF733004CD58F /* Debug */ = {
|
||||
isa = XCBuildConfiguration;
|
||||
buildSettings = {
|
||||
ARCHS = "$(ARCHS_STANDARD)";
|
||||
GCC_PREPROCESSOR_DEFINITIONS = (
|
||||
"$(inherited)",
|
||||
CC_TARGET_OS_MAC,
|
||||
|
@ -8624,7 +8639,6 @@
|
|||
1A0EE31318CDF733004CD58F /* Release */ = {
|
||||
isa = XCBuildConfiguration;
|
||||
buildSettings = {
|
||||
ARCHS = "$(ARCHS_STANDARD)";
|
||||
GCC_PREPROCESSOR_DEFINITIONS = (
|
||||
"$(inherited)",
|
||||
CC_TARGET_OS_MAC,
|
||||
|
@ -8719,7 +8733,6 @@
|
|||
1ABCA2B318CD91520087CE3A /* Debug */ = {
|
||||
isa = XCBuildConfiguration;
|
||||
buildSettings = {
|
||||
ARCHS = "$(ARCHS_STANDARD)";
|
||||
GCC_PREPROCESSOR_DEFINITIONS = (
|
||||
"$(inherited)",
|
||||
CC_TARGET_OS_MAC,
|
||||
|
@ -8739,7 +8752,6 @@
|
|||
1ABCA2B418CD91520087CE3A /* Release */ = {
|
||||
isa = XCBuildConfiguration;
|
||||
buildSettings = {
|
||||
ARCHS = "$(ARCHS_STANDARD)";
|
||||
GCC_PREPROCESSOR_DEFINITIONS = (
|
||||
"$(inherited)",
|
||||
CC_TARGET_OS_MAC,
|
||||
|
@ -8801,7 +8813,6 @@
|
|||
1D6058940D05DD3E006BFB54 /* Debug */ = {
|
||||
isa = XCBuildConfiguration;
|
||||
buildSettings = {
|
||||
ARCHS = "$(ARCHS_STANDARD)";
|
||||
GCC_PREPROCESSOR_DEFINITIONS = (
|
||||
"$(inherited)",
|
||||
CC_TARGET_OS_MAC,
|
||||
|
@ -8815,7 +8826,6 @@
|
|||
1D6058950D05DD3E006BFB54 /* Release */ = {
|
||||
isa = XCBuildConfiguration;
|
||||
buildSettings = {
|
||||
ARCHS = "$(ARCHS_STANDARD)";
|
||||
GCC_PREPROCESSOR_DEFINITIONS = (
|
||||
"$(inherited)",
|
||||
CC_TARGET_OS_MAC,
|
||||
|
|
|
@ -150,8 +150,9 @@ void NodeGrid::visit(Renderer *renderer, const Mat4 &parentTransform, uint32_t p
|
|||
this->draw(renderer, _modelViewTransform, dirty);
|
||||
}
|
||||
|
||||
// reset for next frame
|
||||
_orderOfArrival = 0;
|
||||
// FIX ME: Why need to set _orderOfArrival to 0??
|
||||
// Please refer to https://github.com/cocos2d/cocos2d-x/pull/6920
|
||||
// setOrderOfArrival(0);
|
||||
|
||||
if(_nodeGrid && _nodeGrid->isActive())
|
||||
{
|
||||
|
|
|
@ -330,8 +330,9 @@ void ProtectedNode::visit(Renderer* renderer, const Mat4 &parentTransform, uint3
|
|||
for(auto it=_children.cbegin()+i; it != _children.cend(); ++it)
|
||||
(*it)->visit(renderer, _modelViewTransform, flags);
|
||||
|
||||
// reset for next frame
|
||||
_orderOfArrival = 0;
|
||||
// FIX ME: Why need to set _orderOfArrival to 0??
|
||||
// Please refer to https://github.com/cocos2d/cocos2d-x/pull/6920
|
||||
// setOrderOfArrival(0);
|
||||
|
||||
director->popMatrix(MATRIX_STACK_TYPE::MATRIX_STACK_MODELVIEW);
|
||||
}
|
||||
|
|
|
@ -403,7 +403,9 @@ void RenderTexture::visit(Renderer *renderer, const Mat4 &parentTransform, uint3
|
|||
|
||||
director->popMatrix(MATRIX_STACK_TYPE::MATRIX_STACK_MODELVIEW);
|
||||
|
||||
_orderOfArrival = 0;
|
||||
// FIX ME: Why need to set _orderOfArrival to 0??
|
||||
// Please refer to https://github.com/cocos2d/cocos2d-x/pull/6920
|
||||
// setOrderOfArrival(0);
|
||||
}
|
||||
|
||||
bool RenderTexture::saveToFile(const std::string& filename, bool isRGBA, std::function<void (RenderTexture*, const std::string&)> callback)
|
||||
|
|
|
@ -7,7 +7,7 @@
|
|||
<PropertyGroup />
|
||||
<ItemDefinitionGroup>
|
||||
<ClCompile>
|
||||
<AdditionalIncludeDirectories>$(EngineRoot)cocos;$(EngineRoot)cocos\platform\win32;$(EngineRoot)cocos\platform\desktop;$(EngineRoot)external\glfw3\include\win32;$(EngineRoot)external\win32-specific\gles\include\OGLES</AdditionalIncludeDirectories>
|
||||
<AdditionalIncludeDirectories>$(EngineRoot)cocos;$(EngineRoot)cocos\platform;$(EngineRoot)cocos\platform\desktop;$(EngineRoot)external\glfw3\include\win32;$(EngineRoot)external\win32-specific\gles\include\OGLES</AdditionalIncludeDirectories>
|
||||
<PreprocessorDefinitions>_VARIADIC_MAX=10;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
</ClCompile>
|
||||
<ProjectReference>
|
||||
|
|
|
@ -187,7 +187,7 @@ physics/chipmunk/CCPhysicsWorldInfo_chipmunk.cpp \
|
|||
|
||||
LOCAL_EXPORT_C_INCLUDES := $(LOCAL_PATH) \
|
||||
$(LOCAL_PATH)/. \
|
||||
$(LOCAL_PATH)/platform/android \
|
||||
$(LOCAL_PATH)/platform \
|
||||
$(LOCAL_PATH)/base \
|
||||
$(LOCAL_PATH)/../external/tinyxml2 \
|
||||
$(LOCAL_PATH)/../external/unzip \
|
||||
|
@ -197,7 +197,7 @@ LOCAL_EXPORT_C_INCLUDES := $(LOCAL_PATH) \
|
|||
|
||||
LOCAL_C_INCLUDES := $(LOCAL_PATH) \
|
||||
$(LOCAL_PATH)/. \
|
||||
$(LOCAL_PATH)/platform/android \
|
||||
$(LOCAL_PATH)/platform \
|
||||
$(LOCAL_PATH)/../external \
|
||||
$(LOCAL_PATH)/../external/tinyxml2 \
|
||||
$(LOCAL_PATH)/../external/unzip \
|
||||
|
@ -238,6 +238,7 @@ LOCAL_MODULE := cocos2dx_static
|
|||
LOCAL_MODULE_FILENAME := libcocos2d
|
||||
|
||||
LOCAL_STATIC_LIBRARIES := cocostudio_static
|
||||
LOCAL_STATIC_LIBRARIES += audioengine_static
|
||||
LOCAL_STATIC_LIBRARIES += cocos3d_static
|
||||
LOCAL_STATIC_LIBRARIES += cocosbuilder_static
|
||||
LOCAL_STATIC_LIBRARIES += spine_static
|
||||
|
|
|
@ -296,7 +296,7 @@ if(MACOSX)
|
|||
${COCOS2D_BASE_SRC}
|
||||
ui/UIEditBox/UIEditBoxImpl-ios.mm
|
||||
ui/UIEditBox/UIEditBoxImpl-mac.mm
|
||||
base/CCUserDefault.mm
|
||||
base/CCUserDefault-apple.mm
|
||||
)
|
||||
endif()
|
||||
|
||||
|
|
|
@ -0,0 +1,395 @@
|
|||
/****************************************************************************
|
||||
Copyright (c) 2014 Chukong Technologies Inc.
|
||||
|
||||
http://www.cocos2d-x.org
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in
|
||||
all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
THE SOFTWARE.
|
||||
****************************************************************************/
|
||||
#if CC_TARGET_PLATFORM == CC_PLATFORM_ANDROID || CC_TARGET_PLATFORM == CC_PLATFORM_IOS
|
||||
|
||||
#include "audio/include/AudioEngine.h"
|
||||
#include "platform/CCFileUtils.h"
|
||||
#include "base/ccUtils.h"
|
||||
|
||||
#if CC_TARGET_PLATFORM == CC_PLATFORM_ANDROID
|
||||
#include "android/AudioEngine-inl.h"
|
||||
#elif CC_TARGET_PLATFORM == CC_PLATFORM_IOS
|
||||
#include "ios/AudioEngine-inl.h"
|
||||
#endif
|
||||
|
||||
#define TIME_DELAY_PRECISION 0.0001
|
||||
|
||||
using namespace cocos2d;
|
||||
|
||||
const int AudioEngine::INVAILD_AUDIO_ID = -1;
|
||||
const float AudioEngine::TIME_UNKNOWN = -1.0f;
|
||||
|
||||
//audio file path,audio IDs
|
||||
std::unordered_map<std::string,std::list<int>> AudioEngine::_audioPathIDMap;
|
||||
//profileName,ProfileHelper
|
||||
std::unordered_map<std::string, AudioEngine::ProfileHelper> AudioEngine::_audioPathProfileHelperMap;
|
||||
int AudioEngine::_maxInstances = MAX_AUDIOINSTANCES;
|
||||
AudioEngine::ProfileHelper* AudioEngine::_defaultProfileHelper;
|
||||
std::unordered_map<int, AudioEngine::AudioInfo> AudioEngine::_audioIDInfoMap;
|
||||
AudioEngineImpl* AudioEngine::_audioEngineImpl = nullptr;
|
||||
|
||||
void AudioEngine::end()
|
||||
{
|
||||
delete _audioEngineImpl;
|
||||
_audioEngineImpl = nullptr;
|
||||
|
||||
delete _defaultProfileHelper;
|
||||
_defaultProfileHelper = nullptr;
|
||||
}
|
||||
|
||||
bool AudioEngine::lazyInit()
|
||||
{
|
||||
if (_audioEngineImpl == nullptr)
|
||||
{
|
||||
_audioEngineImpl = new (std::nothrow) AudioEngineImpl();
|
||||
if(!_audioEngineImpl || !_audioEngineImpl->init() ){
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
int AudioEngine::play2d(const std::string& filePath, bool loop, float volume, const AudioProfile *profile)
|
||||
{
|
||||
int ret = AudioEngine::INVAILD_AUDIO_ID;
|
||||
|
||||
do {
|
||||
if ( !lazyInit() ){
|
||||
break;
|
||||
}
|
||||
|
||||
if ( !FileUtils::getInstance()->isFileExist(filePath)){
|
||||
break;
|
||||
}
|
||||
|
||||
ProfileHelper* manage = _defaultProfileHelper;
|
||||
if (profile && profile != &manage->profile){
|
||||
CC_ASSERT(!profile->name.empty());
|
||||
manage = &_audioPathProfileHelperMap[profile->name];
|
||||
manage->profile = *profile;
|
||||
}
|
||||
|
||||
if (_audioIDInfoMap.size() >= _maxInstances) {
|
||||
log("Fail to play %s cause by limited max instance of AudioEngine",filePath.c_str());
|
||||
break;
|
||||
}
|
||||
if (manage)
|
||||
{
|
||||
if(manage->profile.maxInstances != 0 && manage->audioIDs.size() >= manage->profile.maxInstances){
|
||||
log("Fail to play %s cause by limited max instance of AudioProfile",filePath.c_str());
|
||||
break;
|
||||
}
|
||||
if (manage->profile.minDelay > TIME_DELAY_PRECISION) {
|
||||
auto currTime = utils::gettime();
|
||||
if (manage->lastPlayTime > TIME_DELAY_PRECISION && currTime - manage->lastPlayTime <= manage->profile.minDelay) {
|
||||
log("Fail to play %s cause by limited minimum delay",filePath.c_str());
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (volume < 0.0f) {
|
||||
volume = 0.0f;
|
||||
}
|
||||
else if (volume > 1.0f){
|
||||
volume = 1.0f;
|
||||
}
|
||||
|
||||
ret = _audioEngineImpl->play2d(filePath, loop, volume);
|
||||
if (ret != INVAILD_AUDIO_ID)
|
||||
{
|
||||
_audioPathIDMap[filePath].push_back(ret);
|
||||
auto it = _audioPathIDMap.find(filePath);
|
||||
|
||||
auto& audioRef = _audioIDInfoMap[ret];
|
||||
audioRef.volume = volume;
|
||||
audioRef.loop = loop;
|
||||
audioRef.is3dAudio = false;
|
||||
audioRef.filePath = &it->first;
|
||||
|
||||
if (manage) {
|
||||
manage->lastPlayTime = utils::gettime();
|
||||
manage->audioIDs.push_back(ret);
|
||||
}
|
||||
audioRef.profileHelper = manage;
|
||||
}
|
||||
} while (0);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
void AudioEngine::setLoop(int audioID, bool loop)
|
||||
{
|
||||
auto it = _audioIDInfoMap.find(audioID);
|
||||
if (it != _audioIDInfoMap.end() && it->second.loop != loop){
|
||||
_audioEngineImpl->setLoop(audioID, loop);
|
||||
it->second.loop = loop;
|
||||
}
|
||||
}
|
||||
|
||||
void AudioEngine::setVolume(int audioID, float volume)
|
||||
{
|
||||
auto it = _audioIDInfoMap.find(audioID);
|
||||
if (it != _audioIDInfoMap.end()){
|
||||
if (volume < 0.0f) {
|
||||
volume = 0.0f;
|
||||
}
|
||||
else if (volume > 1.0f){
|
||||
volume = 1.0f;
|
||||
}
|
||||
|
||||
if (it->second.volume != volume){
|
||||
_audioEngineImpl->setVolume(audioID, volume);
|
||||
it->second.volume = volume;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void AudioEngine::pause(int audioID)
|
||||
{
|
||||
auto it = _audioIDInfoMap.find(audioID);
|
||||
if (it != _audioIDInfoMap.end() && it->second.state == AudioState::PLAYING){
|
||||
_audioEngineImpl->pause(audioID);
|
||||
it->second.state = AudioState::PAUSED;
|
||||
}
|
||||
}
|
||||
|
||||
void AudioEngine::pauseAll()
|
||||
{
|
||||
auto itEnd = _audioIDInfoMap.end();
|
||||
for (auto it = _audioIDInfoMap.begin(); it != itEnd; ++it)
|
||||
{
|
||||
if (it->second.state == AudioState::PLAYING)
|
||||
{
|
||||
_audioEngineImpl->pause(it->first);
|
||||
it->second.state = AudioState::PAUSED;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void AudioEngine::resume(int audioID)
|
||||
{
|
||||
auto it = _audioIDInfoMap.find(audioID);
|
||||
if (it != _audioIDInfoMap.end() && it->second.state == AudioState::PAUSED){
|
||||
_audioEngineImpl->resume(audioID);
|
||||
it->second.state = AudioState::PLAYING;
|
||||
}
|
||||
}
|
||||
|
||||
void AudioEngine::resumeAll()
|
||||
{
|
||||
auto itEnd = _audioIDInfoMap.end();
|
||||
for (auto it = _audioIDInfoMap.begin(); it != itEnd; ++it)
|
||||
{
|
||||
if (it->second.state == AudioState::PAUSED)
|
||||
{
|
||||
_audioEngineImpl->resume(it->first);
|
||||
it->second.state = AudioState::PLAYING;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void AudioEngine::stop(int audioID)
|
||||
{
|
||||
auto it = _audioIDInfoMap.find(audioID);
|
||||
if (it != _audioIDInfoMap.end()){
|
||||
_audioEngineImpl->stop(audioID);
|
||||
|
||||
remove(audioID);
|
||||
}
|
||||
}
|
||||
|
||||
void AudioEngine::remove(int audioID)
|
||||
{
|
||||
auto it = _audioIDInfoMap.find(audioID);
|
||||
if (it != _audioIDInfoMap.end()){
|
||||
if (it->second.profileHelper) {
|
||||
it->second.profileHelper->audioIDs.remove(audioID);
|
||||
}
|
||||
_audioPathIDMap[*it->second.filePath].remove(audioID);
|
||||
_audioIDInfoMap.erase(audioID);
|
||||
}
|
||||
}
|
||||
|
||||
void AudioEngine::stopAll()
|
||||
{
|
||||
_audioEngineImpl->stopAll();
|
||||
auto itEnd = _audioIDInfoMap.end();
|
||||
for (auto it = _audioIDInfoMap.begin(); it != itEnd; ++it)
|
||||
{
|
||||
if (it->second.profileHelper){
|
||||
it->second.profileHelper->audioIDs.remove(it->first);
|
||||
}
|
||||
}
|
||||
_audioPathIDMap.clear();
|
||||
_audioIDInfoMap.clear();
|
||||
}
|
||||
|
||||
void AudioEngine::uncache(const std::string &filePath)
|
||||
{
|
||||
if(_audioPathIDMap.find(filePath) != _audioPathIDMap.end()){
|
||||
auto itEnd = _audioPathIDMap[filePath].end();
|
||||
for (auto it = _audioPathIDMap[filePath].begin() ; it != itEnd; ++it) {
|
||||
auto audioID = *it;
|
||||
_audioEngineImpl->stop(audioID);
|
||||
|
||||
auto itInfo = _audioIDInfoMap.find(audioID);
|
||||
if (itInfo != _audioIDInfoMap.end()){
|
||||
if (itInfo->second.profileHelper) {
|
||||
itInfo->second.profileHelper->audioIDs.remove(audioID);
|
||||
}
|
||||
_audioIDInfoMap.erase(audioID);
|
||||
}
|
||||
}
|
||||
_audioEngineImpl->uncache(filePath);
|
||||
_audioPathIDMap.erase(filePath);
|
||||
}
|
||||
}
|
||||
|
||||
void AudioEngine::uncacheAll()
|
||||
{
|
||||
stopAll();
|
||||
_audioEngineImpl->uncacheAll();
|
||||
}
|
||||
|
||||
float AudioEngine::getDuration(int audioID)
|
||||
{
|
||||
auto it = _audioIDInfoMap.find(audioID);
|
||||
if (it != _audioIDInfoMap.end() && it->second.state != AudioState::INITIALZING)
|
||||
{
|
||||
if (it->second.duration == TIME_UNKNOWN)
|
||||
{
|
||||
it->second.duration = _audioEngineImpl->getDuration(audioID);
|
||||
}
|
||||
return it->second.duration;
|
||||
}
|
||||
|
||||
return TIME_UNKNOWN;
|
||||
}
|
||||
|
||||
bool AudioEngine::setCurrentTime(int audioID, float time)
|
||||
{
|
||||
auto it = _audioIDInfoMap.find(audioID);
|
||||
if (it != _audioIDInfoMap.end() && it->second.state != AudioState::INITIALZING){
|
||||
return _audioEngineImpl->setCurrentTime(audioID, time);
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
float AudioEngine::getCurrentTime(int audioID)
|
||||
{
|
||||
auto it = _audioIDInfoMap.find(audioID);
|
||||
if (it != _audioIDInfoMap.end() && it->second.state != AudioState::INITIALZING){
|
||||
return _audioEngineImpl->getCurrentTime(audioID);
|
||||
}
|
||||
return 0.0f;
|
||||
}
|
||||
|
||||
void AudioEngine::setFinishCallback(int audioID, const std::function<void (int, const std::string &)> &callback)
|
||||
{
|
||||
auto it = _audioIDInfoMap.find(audioID);
|
||||
if (it != _audioIDInfoMap.end()){
|
||||
_audioEngineImpl->setFinishCallback(audioID, callback);
|
||||
}
|
||||
}
|
||||
|
||||
bool AudioEngine::setMaxAudioInstance(int maxInstances)
|
||||
{
|
||||
if (maxInstances > 0 && maxInstances <= MAX_AUDIOINSTANCES) {
|
||||
_maxInstances = maxInstances;
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
bool AudioEngine::isLoop(int audioID)
|
||||
{
|
||||
auto tmpIterator = _audioIDInfoMap.find(audioID);
|
||||
if (tmpIterator != _audioIDInfoMap.end())
|
||||
{
|
||||
return tmpIterator->second.loop;
|
||||
}
|
||||
|
||||
log("AudioEngine::isLoop-->The audio instance %d is non-existent", audioID);
|
||||
return false;
|
||||
}
|
||||
|
||||
float AudioEngine::getVolume(int audioID)
|
||||
{
|
||||
auto tmpIterator = _audioIDInfoMap.find(audioID);
|
||||
if (tmpIterator != _audioIDInfoMap.end())
|
||||
{
|
||||
return tmpIterator->second.volume;
|
||||
}
|
||||
|
||||
log("AudioEngine::getVolume-->The audio instance %d is non-existent", audioID);
|
||||
return 0.0f;
|
||||
}
|
||||
|
||||
AudioEngine::AudioState AudioEngine::getState(int audioID)
|
||||
{
|
||||
auto tmpIterator = _audioIDInfoMap.find(audioID);
|
||||
if (tmpIterator != _audioIDInfoMap.end())
|
||||
{
|
||||
return tmpIterator->second.state;
|
||||
}
|
||||
|
||||
return AudioState::ERROR;
|
||||
}
|
||||
|
||||
AudioProfile* AudioEngine::getProfile(int audioID)
|
||||
{
|
||||
auto it = _audioIDInfoMap.find(audioID);
|
||||
if (it != _audioIDInfoMap.end())
|
||||
{
|
||||
return &it->second.profileHelper->profile;
|
||||
}
|
||||
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
AudioProfile* AudioEngine::getDefaultProfile()
|
||||
{
|
||||
if (_defaultProfileHelper == nullptr)
|
||||
{
|
||||
_defaultProfileHelper = new (std::nothrow) ProfileHelper();
|
||||
}
|
||||
|
||||
return &_defaultProfileHelper->profile;
|
||||
}
|
||||
|
||||
AudioProfile* AudioEngine::getProfile(const std::string &name)
|
||||
{
|
||||
auto it = _audioPathProfileHelperMap.find(name);
|
||||
if (it != _audioPathProfileHelperMap.end()) {
|
||||
return &it->second.profile;
|
||||
} else {
|
||||
return nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
#endif
|
|
@ -16,3 +16,23 @@ LOCAL_C_INCLUDES := $(LOCAL_PATH)/../include \
|
|||
$(LOCAL_PATH)/../../platform/android
|
||||
|
||||
include $(BUILD_STATIC_LIBRARY)
|
||||
|
||||
#new audio engine
|
||||
include $(CLEAR_VARS)
|
||||
|
||||
LOCAL_MODULE := audioengine_static
|
||||
|
||||
LOCAL_MODULE_FILENAME := libaudioengine
|
||||
|
||||
LOCAL_SRC_FILES := AudioEngine-inl.cpp \
|
||||
../AudioEngine.cpp
|
||||
|
||||
LOCAL_EXPORT_C_INCLUDES := $(LOCAL_PATH)/../include
|
||||
|
||||
LOCAL_EXPORT_LDLIBS := -lOpenSLES
|
||||
|
||||
LOCAL_C_INCLUDES := $(LOCAL_PATH)/../include \
|
||||
$(LOCAL_PATH)/../.. \
|
||||
$(LOCAL_PATH)/../../platform/android
|
||||
|
||||
include $(BUILD_STATIC_LIBRARY)
|
||||
|
|
|
@ -0,0 +1,366 @@
|
|||
/****************************************************************************
|
||||
Copyright (c) 2014 Chukong Technologies Inc.
|
||||
|
||||
http://www.cocos2d-x.org
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in
|
||||
all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
THE SOFTWARE.
|
||||
****************************************************************************/
|
||||
#if CC_TARGET_PLATFORM == CC_PLATFORM_ANDROID
|
||||
#include "AudioEngine-inl.h"
|
||||
|
||||
#include <unordered_map>
|
||||
// for native asset manager
|
||||
#include <sys/types.h>
|
||||
#include <android/asset_manager.h>
|
||||
#include <android/asset_manager_jni.h>
|
||||
|
||||
#include "audio/include/AudioEngine.h"
|
||||
#include "base/CCDirector.h"
|
||||
#include "platform/android/CCFileUtils-android.h"
|
||||
|
||||
#include "platform/android/jni/JniHelper.h"
|
||||
#include <android/log.h>
|
||||
#include <jni.h>
|
||||
|
||||
using namespace cocos2d;
|
||||
|
||||
void PlayOverEvent(SLPlayItf caller, void* context, SLuint32 playEvent)
|
||||
{
|
||||
if (context && playEvent == SL_PLAYEVENT_HEADATEND)
|
||||
{
|
||||
AudioEngineImpl* engineImpl = (AudioEngineImpl*)context;
|
||||
engineImpl->playerFinishCallback(caller,playEvent);
|
||||
}
|
||||
}
|
||||
|
||||
AudioPlayer::AudioPlayer()
|
||||
: _fdPlayerObject(nullptr)
|
||||
, _finishCallback(nullptr)
|
||||
, _duration(0.0f)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
AudioPlayer::~AudioPlayer()
|
||||
{
|
||||
if (_fdPlayerObject)
|
||||
{
|
||||
(*_fdPlayerObject)->Destroy(_fdPlayerObject);
|
||||
_fdPlayerObject = nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
bool AudioPlayer::init(SLEngineItf engineEngine, SLObjectItf outputMixObject,const std::string& fileFullPath, float volume, bool loop)
|
||||
{
|
||||
bool ret = false;
|
||||
|
||||
do
|
||||
{
|
||||
SLDataSource audioSrc;
|
||||
|
||||
SLDataLocator_AndroidFD loc_fd;
|
||||
SLDataLocator_URI loc_uri;
|
||||
|
||||
SLDataFormat_MIME format_mime = {SL_DATAFORMAT_MIME, NULL, SL_CONTAINERTYPE_UNSPECIFIED};
|
||||
audioSrc.pFormat = &format_mime;
|
||||
|
||||
if (fileFullPath[0] != '/'){
|
||||
std::string relativePath = "";
|
||||
|
||||
size_t position = fileFullPath.find("assets/");
|
||||
if (0 == position) {
|
||||
// "assets/" is at the beginning of the path and we don't want it
|
||||
relativePath += fileFullPath.substr(strlen("assets/"));
|
||||
} else {
|
||||
relativePath += fileFullPath;
|
||||
}
|
||||
|
||||
auto asset = AAssetManager_open(cocos2d::FileUtilsAndroid::getAssetManager(), relativePath.c_str(), AASSET_MODE_UNKNOWN);
|
||||
|
||||
// open asset as file descriptor
|
||||
off_t start, length;
|
||||
int fd = AAsset_openFileDescriptor(asset, &start, &length);
|
||||
if (fd <= 0){
|
||||
AAsset_close(asset);
|
||||
break;
|
||||
}
|
||||
AAsset_close(asset);
|
||||
|
||||
// configure audio source
|
||||
loc_fd = {SL_DATALOCATOR_ANDROIDFD, fd, start, length};
|
||||
|
||||
audioSrc.pLocator = &loc_fd;
|
||||
}
|
||||
else{
|
||||
loc_uri = {SL_DATALOCATOR_URI , (SLchar*)fileFullPath.c_str()};
|
||||
audioSrc.pLocator = &loc_uri;
|
||||
}
|
||||
|
||||
// configure audio sink
|
||||
SLDataLocator_OutputMix loc_outmix = {SL_DATALOCATOR_OUTPUTMIX, outputMixObject};
|
||||
SLDataSink audioSnk = {&loc_outmix, NULL};
|
||||
|
||||
// create audio player
|
||||
const SLInterfaceID ids[3] = {SL_IID_SEEK, SL_IID_PREFETCHSTATUS, SL_IID_VOLUME};
|
||||
const SLboolean req[3] = {SL_BOOLEAN_TRUE, SL_BOOLEAN_TRUE, SL_BOOLEAN_TRUE};
|
||||
auto result = (*engineEngine)->CreateAudioPlayer(engineEngine, &_fdPlayerObject, &audioSrc, &audioSnk, 3, ids, req);
|
||||
if(SL_RESULT_SUCCESS != result){ ERRORLOG("create audio player fail"); break; }
|
||||
|
||||
// realize the player
|
||||
result = (*_fdPlayerObject)->Realize(_fdPlayerObject, SL_BOOLEAN_FALSE);
|
||||
if(SL_RESULT_SUCCESS != result){ ERRORLOG("realize the player fail"); break; }
|
||||
|
||||
// get the play interface
|
||||
result = (*_fdPlayerObject)->GetInterface(_fdPlayerObject, SL_IID_PLAY, &_fdPlayerPlay);
|
||||
if(SL_RESULT_SUCCESS != result){ ERRORLOG("get the play interface fail"); break; }
|
||||
|
||||
// get the seek interface
|
||||
result = (*_fdPlayerObject)->GetInterface(_fdPlayerObject, SL_IID_SEEK, &_fdPlayerSeek);
|
||||
if(SL_RESULT_SUCCESS != result){ ERRORLOG("get the seek interface fail"); break; }
|
||||
|
||||
// get the volume interface
|
||||
result = (*_fdPlayerObject)->GetInterface(_fdPlayerObject, SL_IID_VOLUME, &_fdPlayerVolume);
|
||||
if(SL_RESULT_SUCCESS != result){ ERRORLOG("get the volume interface fail"); break; }
|
||||
|
||||
if (loop){
|
||||
(*_fdPlayerSeek)->SetLoop(_fdPlayerSeek, SL_BOOLEAN_TRUE, 0, SL_TIME_UNKNOWN);
|
||||
}
|
||||
|
||||
int dbVolume = 2000 * log10(volume);
|
||||
if(dbVolume < SL_MILLIBEL_MIN){
|
||||
dbVolume = SL_MILLIBEL_MIN;
|
||||
}
|
||||
(*_fdPlayerVolume)->SetVolumeLevel(_fdPlayerVolume, dbVolume);
|
||||
|
||||
result = (*_fdPlayerPlay)->SetPlayState(_fdPlayerPlay, SL_PLAYSTATE_PLAYING);
|
||||
if(SL_RESULT_SUCCESS != result){ ERRORLOG("SetPlayState fail"); break; }
|
||||
|
||||
ret = true;
|
||||
} while (0);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
//====================================================
|
||||
AudioEngineImpl::AudioEngineImpl()
|
||||
: currentAudioID(0)
|
||||
, _engineObject(nullptr)
|
||||
, _engineEngine(nullptr)
|
||||
, _outputMixObject(nullptr)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
AudioEngineImpl::~AudioEngineImpl()
|
||||
{
|
||||
if (_outputMixObject)
|
||||
{
|
||||
(*_outputMixObject)->Destroy(_outputMixObject);
|
||||
}
|
||||
if (_engineObject)
|
||||
{
|
||||
(*_engineObject)->Destroy(_engineObject);
|
||||
}
|
||||
}
|
||||
|
||||
bool AudioEngineImpl::init()
|
||||
{
|
||||
bool ret = false;
|
||||
do{
|
||||
// create engine
|
||||
auto result = slCreateEngine(&_engineObject, 0, nullptr, 0, nullptr, nullptr);
|
||||
if(SL_RESULT_SUCCESS != result){ ERRORLOG("create opensl engine fail"); break; }
|
||||
|
||||
// realize the engine
|
||||
result = (*_engineObject)->Realize(_engineObject, SL_BOOLEAN_FALSE);
|
||||
if(SL_RESULT_SUCCESS != result){ ERRORLOG("realize the engine fail"); break; }
|
||||
|
||||
// get the engine interface, which is needed in order to create other objects
|
||||
result = (*_engineObject)->GetInterface(_engineObject, SL_IID_ENGINE, &_engineEngine);
|
||||
if(SL_RESULT_SUCCESS != result){ ERRORLOG("get the engine interface fail"); break; }
|
||||
|
||||
// create output mix
|
||||
const SLInterfaceID outputMixIIDs[] = {};
|
||||
const SLboolean outputMixReqs[] = {};
|
||||
result = (*_engineEngine)->CreateOutputMix(_engineEngine, &_outputMixObject, 0, outputMixIIDs, outputMixReqs);
|
||||
if(SL_RESULT_SUCCESS != result){ ERRORLOG("create output mix fail"); break; }
|
||||
|
||||
// realize the output mix
|
||||
result = (*_outputMixObject)->Realize(_outputMixObject, SL_BOOLEAN_FALSE);
|
||||
if(SL_RESULT_SUCCESS != result){ ERRORLOG("realize the output mix fail"); break; }
|
||||
|
||||
ret = true;
|
||||
}while (false);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
int AudioEngineImpl::play2d(const std::string &fileFullPath ,bool loop ,float volume)
|
||||
{
|
||||
auto audioId = AudioEngine::INVAILD_AUDIO_ID;
|
||||
|
||||
do
|
||||
{
|
||||
if (_engineEngine == nullptr)
|
||||
break;
|
||||
|
||||
auto& player = _audioPlayers[currentAudioID];
|
||||
auto initPlayer = player.init( _engineEngine, _outputMixObject, fileFullPath, volume, loop);
|
||||
if (!initPlayer){
|
||||
_audioPlayers.erase(currentAudioID);
|
||||
log("%s,%d message:create player for %s fail", __func__, __LINE__, fileFullPath.c_str());
|
||||
break;
|
||||
}
|
||||
|
||||
audioId = currentAudioID++;
|
||||
player._audioID = audioId;
|
||||
|
||||
(*(player._fdPlayerPlay))->RegisterCallback(player._fdPlayerPlay, PlayOverEvent, (void*)this);
|
||||
(*(player._fdPlayerPlay))->SetCallbackEventsMask(player._fdPlayerPlay, SL_PLAYEVENT_HEADATEND);
|
||||
|
||||
AudioEngine::_audioIDInfoMap[audioId].state = AudioEngine::AudioState::PLAYING;
|
||||
} while (0);
|
||||
|
||||
return audioId;
|
||||
}
|
||||
|
||||
void AudioEngineImpl::playerFinishCallback(SLPlayItf caller, SLuint32 playEvent)
|
||||
{
|
||||
auto itend = _audioPlayers.end();
|
||||
for (auto iter = _audioPlayers.begin(); iter != itend; ++iter)
|
||||
{
|
||||
if (iter->second._fdPlayerPlay == caller)
|
||||
{
|
||||
if (iter->second._finishCallback)
|
||||
{
|
||||
iter->second._finishCallback(iter->second._audioID, *AudioEngine::_audioIDInfoMap[iter->second._audioID].filePath);
|
||||
}
|
||||
AudioEngine::stop(iter->second._audioID);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void AudioEngineImpl::setVolume(int audioID,float volume)
|
||||
{
|
||||
auto& player = _audioPlayers[audioID];
|
||||
int dbVolume = 2000 * log10(volume);
|
||||
if(dbVolume < SL_MILLIBEL_MIN){
|
||||
dbVolume = SL_MILLIBEL_MIN;
|
||||
}
|
||||
auto result = (*player._fdPlayerVolume)->SetVolumeLevel(player._fdPlayerVolume, dbVolume);
|
||||
if(SL_RESULT_SUCCESS != result){
|
||||
log("%s error:%lu",__func__, result);
|
||||
}
|
||||
}
|
||||
|
||||
void AudioEngineImpl::setLoop(int audioID, bool loop)
|
||||
{
|
||||
auto& player = _audioPlayers[audioID];
|
||||
SLboolean loopEnabled = SL_BOOLEAN_TRUE;
|
||||
if (!loop){
|
||||
loopEnabled = SL_BOOLEAN_FALSE;
|
||||
}
|
||||
(*player._fdPlayerSeek)->SetLoop(player._fdPlayerSeek, loopEnabled, 0, SL_TIME_UNKNOWN);
|
||||
}
|
||||
|
||||
void AudioEngineImpl::pause(int audioID)
|
||||
{
|
||||
auto& player = _audioPlayers[audioID];
|
||||
auto result = (*player._fdPlayerPlay)->SetPlayState(player._fdPlayerPlay, SL_PLAYSTATE_PAUSED);
|
||||
if(SL_RESULT_SUCCESS != result){
|
||||
log("%s error:%lu",__func__, result);
|
||||
}
|
||||
}
|
||||
|
||||
void AudioEngineImpl::resume(int audioID)
|
||||
{
|
||||
auto& player = _audioPlayers[audioID];
|
||||
auto result = (*player._fdPlayerPlay)->SetPlayState(player._fdPlayerPlay, SL_PLAYSTATE_PLAYING);
|
||||
if(SL_RESULT_SUCCESS != result){
|
||||
log("%s error:%lu",__func__, result);
|
||||
}
|
||||
}
|
||||
|
||||
void AudioEngineImpl::stop(int audioID)
|
||||
{
|
||||
auto& player = _audioPlayers[audioID];
|
||||
auto result = (*player._fdPlayerPlay)->SetPlayState(player._fdPlayerPlay, SL_PLAYSTATE_STOPPED);
|
||||
if(SL_RESULT_SUCCESS != result){
|
||||
log("%s error:%lu",__func__, result);
|
||||
}
|
||||
|
||||
_audioPlayers.erase(audioID);
|
||||
}
|
||||
|
||||
void AudioEngineImpl::stopAll()
|
||||
{
|
||||
auto itEnd = _audioPlayers.end();
|
||||
for (auto it = _audioPlayers.begin(); it != itEnd; ++it)
|
||||
{
|
||||
auto result = (*it->second._fdPlayerPlay)->SetPlayState(it->second._fdPlayerPlay, SL_PLAYSTATE_STOPPED);
|
||||
}
|
||||
_audioPlayers.clear();
|
||||
}
|
||||
|
||||
float AudioEngineImpl::getDuration(int audioID)
|
||||
{
|
||||
SLmillisecond duration;
|
||||
auto& player = _audioPlayers[audioID];
|
||||
auto result = (*player._fdPlayerPlay)->GetDuration(player._fdPlayerPlay, &duration);
|
||||
if (duration == SL_TIME_UNKNOWN){
|
||||
return AudioEngine::TIME_UNKNOWN;
|
||||
}
|
||||
else{
|
||||
player._duration = duration / 1000.0;
|
||||
|
||||
if (player._duration <= 0)
|
||||
{
|
||||
return AudioEngine::TIME_UNKNOWN;
|
||||
}
|
||||
|
||||
return player._duration;
|
||||
}
|
||||
}
|
||||
|
||||
float AudioEngineImpl::getCurrentTime(int audioID)
|
||||
{
|
||||
SLmillisecond currPos;
|
||||
auto& player = _audioPlayers[audioID];
|
||||
(*player._fdPlayerPlay)->GetPosition(player._fdPlayerPlay, &currPos);
|
||||
return currPos / 1000.0f;
|
||||
}
|
||||
|
||||
bool AudioEngineImpl::setCurrentTime(int audioID, float time)
|
||||
{
|
||||
auto& player = _audioPlayers[audioID];
|
||||
SLmillisecond pos = 1000 * time;
|
||||
auto result = (*player._fdPlayerSeek)->SetPosition(player._fdPlayerSeek, pos, SL_SEEKMODE_ACCURATE);
|
||||
if(SL_RESULT_SUCCESS != result){
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
void AudioEngineImpl::setFinishCallback(int audioID, const std::function<void (int, const std::string &)> &callback)
|
||||
{
|
||||
_audioPlayers[audioID]._finishCallback = callback;
|
||||
}
|
||||
|
||||
#endif
|
|
@ -0,0 +1,108 @@
|
|||
/****************************************************************************
|
||||
Copyright (c) 2014 Chukong Technologies Inc.
|
||||
|
||||
http://www.cocos2d-x.org
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in
|
||||
all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
THE SOFTWARE.
|
||||
****************************************************************************/
|
||||
#if CC_TARGET_PLATFORM == CC_PLATFORM_ANDROID
|
||||
|
||||
#ifndef __AUDIO_ENGINE_INL_H_
|
||||
#define __AUDIO_ENGINE_INL_H_
|
||||
|
||||
#include <SLES/OpenSLES.h>
|
||||
#include <SLES/OpenSLES_Android.h>
|
||||
#include <string>
|
||||
#include <unordered_map>
|
||||
#include "base/ccUtils.h"
|
||||
|
||||
#define MAX_AUDIOINSTANCES 24
|
||||
|
||||
#define ERRORLOG(msg) log("fun:%s,line:%d,msg:%s",__func__,__LINE__,#msg)
|
||||
|
||||
NS_CC_BEGIN
|
||||
|
||||
class AudioEngineImpl;
|
||||
|
||||
class AudioPlayer
|
||||
{
|
||||
public:
|
||||
AudioPlayer();
|
||||
~AudioPlayer();
|
||||
|
||||
bool init(SLEngineItf engineEngine, SLObjectItf outputMixObject,const std::string& fileFullPath, float volume, bool loop);
|
||||
|
||||
private:
|
||||
|
||||
SLObjectItf _fdPlayerObject;
|
||||
SLPlayItf _fdPlayerPlay;
|
||||
SLSeekItf _fdPlayerSeek;
|
||||
SLVolumeItf _fdPlayerVolume;
|
||||
|
||||
float _duration;
|
||||
int _audioID;
|
||||
|
||||
std::function<void (int, const std::string &)> _finishCallback;
|
||||
|
||||
friend class AudioEngineImpl;
|
||||
};
|
||||
|
||||
class AudioEngineImpl
|
||||
{
|
||||
public:
|
||||
AudioEngineImpl();
|
||||
~AudioEngineImpl();
|
||||
|
||||
bool init();
|
||||
int play2d(const std::string &fileFullPath ,bool loop ,float volume);
|
||||
void setVolume(int audioID,float volume);
|
||||
void setLoop(int audioID, bool loop);
|
||||
void pause(int audioID);
|
||||
void resume(int audioID);
|
||||
void stop(int audioID);
|
||||
void stopAll();
|
||||
float getDuration(int audioID);
|
||||
float getCurrentTime(int audioID);
|
||||
bool setCurrentTime(int audioID, float time);
|
||||
void setFinishCallback(int audioID, const std::function<void (int, const std::string &)> &callback);
|
||||
|
||||
void playerFinishCallback(SLPlayItf caller, SLuint32 playEvent);
|
||||
|
||||
void uncache(const std::string& filePath){}
|
||||
void uncacheAll(){}
|
||||
private:
|
||||
|
||||
// engine interfaces
|
||||
SLObjectItf _engineObject;
|
||||
SLEngineItf _engineEngine;
|
||||
|
||||
// output mix interfaces
|
||||
SLObjectItf _outputMixObject;
|
||||
|
||||
//audioID,AudioInfo
|
||||
std::unordered_map<int, AudioPlayer> _audioPlayers;
|
||||
|
||||
int currentAudioID;
|
||||
};
|
||||
|
||||
#endif // __AUDIO_ENGINE_INL_H_
|
||||
|
||||
NS_CC_END
|
||||
|
||||
#endif
|
|
@ -0,0 +1,271 @@
|
|||
/****************************************************************************
|
||||
Copyright (c) 2014 Chukong Technologies Inc.
|
||||
|
||||
http://www.cocos2d-x.org
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in
|
||||
all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
THE SOFTWARE.
|
||||
****************************************************************************/
|
||||
#if CC_TARGET_PLATFORM == CC_PLATFORM_ANDROID || CC_TARGET_PLATFORM == CC_PLATFORM_IOS
|
||||
#ifndef __AUDIO_ENGINE_H_
|
||||
#define __AUDIO_ENGINE_H_
|
||||
|
||||
#include <string.h>
|
||||
#include <unordered_map>
|
||||
|
||||
#include "2d/CCNode.h"
|
||||
#include "Export.h"
|
||||
|
||||
#ifdef ERROR
|
||||
#undef ERROR
|
||||
#endif // ERROR
|
||||
|
||||
NS_CC_BEGIN
|
||||
|
||||
class EXPORT_DLL AudioProfile
|
||||
{
|
||||
public:
|
||||
//name can't be empty
|
||||
std::string name;
|
||||
|
||||
unsigned int maxInstances;
|
||||
|
||||
/* minimum delay in between sounds */
|
||||
double minDelay;
|
||||
|
||||
AudioProfile()
|
||||
: minDelay(0.0)
|
||||
, maxInstances(0)
|
||||
{
|
||||
|
||||
}
|
||||
};
|
||||
|
||||
class AudioEngineImpl;
|
||||
|
||||
/**
|
||||
@class AudioEngine
|
||||
@brief
|
||||
@note
|
||||
*/
|
||||
|
||||
class EXPORT_DLL AudioEngine
|
||||
{
|
||||
public:
|
||||
enum class AudioState
|
||||
{
|
||||
ERROR = -1,
|
||||
INITIALZING,
|
||||
PLAYING,
|
||||
PAUSED
|
||||
};
|
||||
|
||||
static const int INVAILD_AUDIO_ID;
|
||||
|
||||
static const float TIME_UNKNOWN;
|
||||
|
||||
static bool lazyInit();
|
||||
/**
|
||||
* Release related objects
|
||||
@warning It must be called before the application exit
|
||||
*/
|
||||
static void end();
|
||||
|
||||
/** Gets the default profile of audio instances
|
||||
* @return the default profile of audio instances
|
||||
*/
|
||||
static AudioProfile* getDefaultProfile();
|
||||
|
||||
/** Play 2d sound
|
||||
* @param filePath The path of an audio file
|
||||
* @param loop Whether audio instance loop or not
|
||||
* @param volume volume value (range from 0.0 to 1.0)
|
||||
* @param profile a profile for audio instance
|
||||
* @return an audio ID. It allows you to dynamically change the behavior of an audio instance on the fly.
|
||||
*/
|
||||
static int play2d(const std::string& filePath, bool loop = false, float volume = 1.0f, const AudioProfile *profile = nullptr);
|
||||
|
||||
/** Sets whether an audio instance loop or not.
|
||||
@param audioID an audioID returned by the play2d function
|
||||
@param loop Whether audio instance loop or not
|
||||
*/
|
||||
static void setLoop(int audioID, bool loop);
|
||||
|
||||
/** Checks whether an audio instance is loop.
|
||||
* @param audioID an audioID returned by the play2d function
|
||||
* @return Whether or not an audio instance is loop.
|
||||
*/
|
||||
static bool isLoop(int audioID);
|
||||
|
||||
/** Sets volume for an audio instance.
|
||||
* @param audioID an audioID returned by the play2d function
|
||||
* @param volume volume value (range from 0.0 to 1.0)
|
||||
*/
|
||||
static void setVolume(int audioID, float volume);
|
||||
|
||||
/** Gets the volume value of an audio instance.
|
||||
* @param audioID an audioID returned by the play2d function
|
||||
* @return volume value (range from 0.0 to 1.0)
|
||||
*/
|
||||
static float getVolume(int audioID);
|
||||
|
||||
/** Pause an audio instance.
|
||||
* @param audioID an audioID returned by the play2d function
|
||||
*/
|
||||
static void pause(int audioID);
|
||||
|
||||
/** Pause all playing audio instances */
|
||||
static void pauseAll();
|
||||
|
||||
/** Resume an audio instance.
|
||||
* @param audioID an audioID returned by the play2d function
|
||||
*/
|
||||
static void resume(int audioID);
|
||||
|
||||
/** Resume all suspended audio instances */
|
||||
static void resumeAll();
|
||||
|
||||
/** Stop an audio instance.
|
||||
* @param audioID an audioID returned by the play2d function
|
||||
*/
|
||||
static void stop(int audioID);
|
||||
|
||||
/** Stop all audio instances */
|
||||
static void stopAll();
|
||||
|
||||
/** Sets the current playback position of an audio instance.
|
||||
* @param audioID an audioID returned by the play2d function
|
||||
* @return
|
||||
*/
|
||||
static bool setCurrentTime(int audioID, float time);
|
||||
|
||||
/** Gets the current playback position of an audio instance.
|
||||
* @param audioID an audioID returned by the play2d function
|
||||
* @return the current playback position of an audio instance
|
||||
*/
|
||||
static float getCurrentTime(int audioID);
|
||||
|
||||
/** Gets the duration of an audio instance.
|
||||
* @param audioID an audioID returned by the play2d function
|
||||
* @return the duration of an audio instance
|
||||
*/
|
||||
static float getDuration(int audioID);
|
||||
|
||||
/** Returns the state of an audio instance.
|
||||
* @param audioID an audioID returned by the play2d function
|
||||
* @return the status of an audio instance
|
||||
*/
|
||||
static AudioState getState(int audioID);
|
||||
|
||||
/** Register a callback to be invoked when an audio instance has completed playing.
|
||||
* @param audioID an audioID returned by the play2d function
|
||||
* @param callback
|
||||
*/
|
||||
static void setFinishCallback(int audioID, const std::function<void(int,const std::string&)>& callback);
|
||||
|
||||
static int getMaxAudioInstance() {return _maxInstances;}
|
||||
|
||||
static bool setMaxAudioInstance(int maxInstances);
|
||||
|
||||
/** Uncache the audio data from internal buffer.
|
||||
* AudioEngine cache audio data on ios platform
|
||||
* @warning This can lead to stop related audio first.
|
||||
* @param filePath The path of an audio file
|
||||
*/
|
||||
static void uncache(const std::string& filePath);
|
||||
|
||||
/** Uncache all audio data from internal buffer.
|
||||
* @warning All audio will be stopped first.
|
||||
* @param
|
||||
*/
|
||||
static void uncacheAll();
|
||||
|
||||
/** Gets the audio profile by id of audio instance.
|
||||
* @param audioID an audioID returned by the play2d function
|
||||
* @return the audio profile
|
||||
*/
|
||||
static AudioProfile* getProfile(int audioID);
|
||||
|
||||
/** Gets the audio profile by name.
|
||||
* @param name name of audio profile
|
||||
* @return the audio profile
|
||||
*/
|
||||
static AudioProfile* getProfile(const std::string &name);
|
||||
|
||||
protected:
|
||||
|
||||
static void remove(int audioID);
|
||||
|
||||
struct ProfileHelper
|
||||
{
|
||||
AudioProfile profile;
|
||||
|
||||
std::list<int> audioIDs;
|
||||
|
||||
double lastPlayTime;
|
||||
|
||||
ProfileHelper()
|
||||
: lastPlayTime(0.0)
|
||||
{
|
||||
|
||||
}
|
||||
};
|
||||
|
||||
struct AudioInfo
|
||||
{
|
||||
const std::string* filePath;
|
||||
ProfileHelper* profileHelper;
|
||||
|
||||
float volume;
|
||||
bool loop;
|
||||
float duration;
|
||||
AudioState state;
|
||||
|
||||
bool is3dAudio;
|
||||
|
||||
AudioInfo()
|
||||
: profileHelper(nullptr)
|
||||
, duration(TIME_UNKNOWN)
|
||||
, state(AudioState::INITIALZING)
|
||||
{
|
||||
|
||||
}
|
||||
};
|
||||
|
||||
//audioID,audioAttribute
|
||||
static std::unordered_map<int, AudioInfo> _audioIDInfoMap;
|
||||
|
||||
//audio file path,audio IDs
|
||||
static std::unordered_map<std::string,std::list<int>> _audioPathIDMap;
|
||||
|
||||
//profileName,ProfileHelper
|
||||
static std::unordered_map<std::string, ProfileHelper> _audioPathProfileHelperMap;
|
||||
|
||||
static int _maxInstances;
|
||||
|
||||
static ProfileHelper* _defaultProfileHelper;
|
||||
|
||||
static AudioEngineImpl* _audioEngineImpl;
|
||||
|
||||
friend class AudioEngineImpl;
|
||||
};
|
||||
|
||||
NS_CC_END
|
||||
|
||||
#endif // __AUDIO_ENGINE_H_
|
||||
#endif
|
|
@ -0,0 +1,98 @@
|
|||
/****************************************************************************
|
||||
Copyright (c) 2014 Chukong Technologies Inc.
|
||||
|
||||
http://www.cocos2d-x.org
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in
|
||||
all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
THE SOFTWARE.
|
||||
****************************************************************************/
|
||||
#if CC_TARGET_PLATFORM == CC_PLATFORM_IOS
|
||||
|
||||
#ifndef __AUDIO_CACHE_H_
|
||||
#define __AUDIO_CACHE_H_
|
||||
|
||||
#import <OpenAL/al.h>
|
||||
#import <AudioToolbox/AudioToolbox.h>
|
||||
|
||||
#include <string>
|
||||
#include <mutex>
|
||||
#include <vector>
|
||||
|
||||
#include "CCPlatformMacros.h"
|
||||
|
||||
#define QUEUEBUFFER_NUM 3
|
||||
#define QUEUEBUFFER_TIME_STEP 0.1
|
||||
|
||||
NS_CC_BEGIN
|
||||
|
||||
class AudioEngineImpl;
|
||||
class AudioPlayer;
|
||||
|
||||
class AudioCache{
|
||||
public:
|
||||
AudioCache();
|
||||
~AudioCache();
|
||||
|
||||
void addCallbacks(const std::function<void()> &callback);
|
||||
|
||||
private:
|
||||
|
||||
void readDataTask();
|
||||
|
||||
void invokingCallbacks();
|
||||
|
||||
//pcm data related stuff
|
||||
ALsizei _dataSize;
|
||||
ALenum _format;
|
||||
ALsizei _sampleRate;
|
||||
float _duration;
|
||||
int _bytesPerFrame;
|
||||
AudioStreamBasicDescription outputFormat;
|
||||
|
||||
/*Cache related stuff;
|
||||
* Cache pcm data when sizeInBytes less than PCMDATA_CACHEMAXSIZE
|
||||
*/
|
||||
ALuint _alBufferId;
|
||||
char* _pcmData;
|
||||
SInt64 _bytesOfRead;
|
||||
|
||||
/*Queue buffer related stuff
|
||||
* Streaming in openal when sizeInBytes greater then PCMDATA_CACHEMAXSIZE
|
||||
*/
|
||||
char* _queBuffers[QUEUEBUFFER_NUM];
|
||||
UInt32 _queBufferFrames;
|
||||
UInt32 _queBufferBytes;
|
||||
|
||||
bool _alBufferReady;
|
||||
std::mutex _callbackMutex;
|
||||
|
||||
std::vector< std::function<void()> > _callbacks;
|
||||
std::mutex _readDataTaskMutex;
|
||||
|
||||
bool _exitReadDataTask;
|
||||
std::string _fileFullPath;
|
||||
|
||||
friend class AudioEngineImpl;
|
||||
friend class AudioPlayer;
|
||||
} ;
|
||||
|
||||
NS_CC_END
|
||||
|
||||
#endif // __AUDIO_CACHE_H_
|
||||
#endif
|
||||
|
|
@ -0,0 +1,239 @@
|
|||
/****************************************************************************
|
||||
Copyright (c) 2014 Chukong Technologies Inc.
|
||||
|
||||
http://www.cocos2d-x.org
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in
|
||||
all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
THE SOFTWARE.
|
||||
****************************************************************************/
|
||||
#include "AudioCache.h"
|
||||
#include <thread>
|
||||
#import <OpenAL/alc.h>
|
||||
#import <AudioToolbox/ExtendedAudioFile.h>
|
||||
|
||||
#define PCMDATA_CACHEMAXSIZE 1048576
|
||||
|
||||
typedef ALvoid AL_APIENTRY (*alBufferDataStaticProcPtr) (const ALint bid, ALenum format, ALvoid* data, ALsizei size, ALsizei freq);
|
||||
static ALvoid alBufferDataStaticProc(const ALint bid, ALenum format, ALvoid* data, ALsizei size, ALsizei freq)
|
||||
{
|
||||
static alBufferDataStaticProcPtr proc = NULL;
|
||||
|
||||
if (proc == NULL){
|
||||
proc = (alBufferDataStaticProcPtr) alcGetProcAddress(NULL, (const ALCchar*) "alBufferDataStatic");
|
||||
}
|
||||
|
||||
if (proc){
|
||||
proc(bid, format, data, size, freq);
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
using namespace cocos2d;
|
||||
|
||||
AudioCache::AudioCache()
|
||||
: _pcmData(nullptr)
|
||||
, _dataSize(0)
|
||||
, _bytesOfRead(0)
|
||||
, _exitReadDataTask(false)
|
||||
, _queBufferFrames(0)
|
||||
, _queBufferBytes(0)
|
||||
, _alBufferReady(false)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
AudioCache::~AudioCache()
|
||||
{
|
||||
_exitReadDataTask = true;
|
||||
if(_pcmData){
|
||||
if (_alBufferReady){
|
||||
alDeleteBuffers(1, &_alBufferId);
|
||||
}
|
||||
//wait for the 'readDataTask' task to exit
|
||||
_readDataTaskMutex.lock();
|
||||
_readDataTaskMutex.unlock();
|
||||
|
||||
free(_pcmData);
|
||||
}
|
||||
|
||||
if (_queBufferFrames > 0) {
|
||||
for (int index = 0; index < QUEUEBUFFER_NUM; ++index) {
|
||||
free(_queBuffers[index]);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void AudioCache::readDataTask()
|
||||
{
|
||||
_readDataTaskMutex.lock();
|
||||
|
||||
AudioStreamBasicDescription theFileFormat;
|
||||
UInt32 thePropertySize = sizeof(theFileFormat);
|
||||
|
||||
SInt64 theFileLengthInFrames;
|
||||
SInt64 readInFrames;
|
||||
SInt64 dataSize;
|
||||
SInt64 frames;
|
||||
AudioBufferList theDataBuffer;
|
||||
ExtAudioFileRef extRef = nullptr;
|
||||
|
||||
auto fileURL = (CFURLRef)[[NSURL fileURLWithPath:[NSString stringWithCString:_fileFullPath.c_str() encoding:[NSString defaultCStringEncoding]]] retain];
|
||||
|
||||
auto error = ExtAudioFileOpenURL(fileURL, &extRef);
|
||||
if(error) {
|
||||
printf("%s: ExtAudioFileOpenURL FAILED, Error = %d\n", __PRETTY_FUNCTION__, error);
|
||||
goto ExitThread;
|
||||
}
|
||||
|
||||
// Get the audio data format
|
||||
error = ExtAudioFileGetProperty(extRef, kExtAudioFileProperty_FileDataFormat, &thePropertySize, &theFileFormat);
|
||||
if(error) {
|
||||
printf("%s: ExtAudioFileGetProperty(kExtAudioFileProperty_FileDataFormat) FAILED, Error = %d\n", __PRETTY_FUNCTION__, error);
|
||||
goto ExitThread;
|
||||
}
|
||||
if (theFileFormat.mChannelsPerFrame > 2) {
|
||||
printf("%s: Unsupported Format, channel count is greater than stereo\n",__PRETTY_FUNCTION__);
|
||||
goto ExitThread;
|
||||
}
|
||||
|
||||
// Set the client format to 16 bit signed integer (native-endian) data
|
||||
// Maintain the channel count and sample rate of the original source format
|
||||
outputFormat.mSampleRate = theFileFormat.mSampleRate;
|
||||
outputFormat.mChannelsPerFrame = theFileFormat.mChannelsPerFrame;
|
||||
|
||||
_bytesPerFrame = 2 * outputFormat.mChannelsPerFrame;
|
||||
outputFormat.mFormatID = kAudioFormatLinearPCM;
|
||||
outputFormat.mBytesPerPacket = _bytesPerFrame;
|
||||
outputFormat.mFramesPerPacket = 1;
|
||||
outputFormat.mBytesPerFrame = _bytesPerFrame;
|
||||
outputFormat.mBitsPerChannel = 16;
|
||||
outputFormat.mFormatFlags = kAudioFormatFlagsNativeEndian | kAudioFormatFlagIsPacked | kAudioFormatFlagIsSignedInteger;
|
||||
|
||||
error = ExtAudioFileSetProperty(extRef, kExtAudioFileProperty_ClientDataFormat, sizeof(outputFormat), &outputFormat);
|
||||
if(error) {
|
||||
printf("%s: ExtAudioFileSetProperty FAILED, Error = %d\n", __PRETTY_FUNCTION__, error);
|
||||
goto ExitThread;
|
||||
}
|
||||
|
||||
// Get the total frame count
|
||||
thePropertySize = sizeof(theFileLengthInFrames);
|
||||
error = ExtAudioFileGetProperty(extRef, kExtAudioFileProperty_FileLengthFrames, &thePropertySize, &theFileLengthInFrames);
|
||||
if(error) {
|
||||
printf("%s: ExtAudioFileGetProperty(kExtAudioFileProperty_FileLengthFrames) FAILED, Error = %d\n", __PRETTY_FUNCTION__, error);
|
||||
goto ExitThread;
|
||||
}
|
||||
|
||||
_dataSize = (ALsizei)(theFileLengthInFrames * outputFormat.mBytesPerFrame);
|
||||
_format = (outputFormat.mChannelsPerFrame > 1) ? AL_FORMAT_STEREO16 : AL_FORMAT_MONO16;
|
||||
_sampleRate = (ALsizei)outputFormat.mSampleRate;
|
||||
_duration = 1.0f * theFileLengthInFrames / outputFormat.mSampleRate;
|
||||
|
||||
if (_dataSize <= PCMDATA_CACHEMAXSIZE) {
|
||||
_pcmData = (char*)malloc(_dataSize);
|
||||
alGenBuffers(1, &_alBufferId);
|
||||
auto alError = alGetError();
|
||||
if (alError != AL_NO_ERROR) {
|
||||
printf("%s: attaching audio to buffer fail: %x\n", __PRETTY_FUNCTION__, alError);
|
||||
goto ExitThread;
|
||||
}
|
||||
alBufferDataStaticProc(_alBufferId, _format, _pcmData, _dataSize, _sampleRate);
|
||||
|
||||
readInFrames = theFileFormat.mSampleRate * QUEUEBUFFER_TIME_STEP * QUEUEBUFFER_NUM;
|
||||
dataSize = outputFormat.mBytesPerFrame * readInFrames;
|
||||
if (dataSize > _dataSize) {
|
||||
dataSize = _dataSize;
|
||||
readInFrames = theFileLengthInFrames;
|
||||
}
|
||||
theDataBuffer.mNumberBuffers = 1;
|
||||
theDataBuffer.mBuffers[0].mDataByteSize = (UInt32)dataSize;
|
||||
theDataBuffer.mBuffers[0].mNumberChannels = outputFormat.mChannelsPerFrame;
|
||||
|
||||
theDataBuffer.mBuffers[0].mData = _pcmData;
|
||||
frames = readInFrames;
|
||||
ExtAudioFileRead(extRef, (UInt32*)&frames, &theDataBuffer);
|
||||
_alBufferReady = true;
|
||||
_bytesOfRead += dataSize;
|
||||
invokingCallbacks();
|
||||
|
||||
while (!_exitReadDataTask && _bytesOfRead + dataSize < _dataSize) {
|
||||
theDataBuffer.mBuffers[0].mData = _pcmData + _bytesOfRead;
|
||||
frames = readInFrames;
|
||||
ExtAudioFileRead(extRef, (UInt32*)&frames, &theDataBuffer);
|
||||
_bytesOfRead += dataSize;
|
||||
}
|
||||
|
||||
dataSize = _dataSize - _bytesOfRead;
|
||||
if (!_exitReadDataTask && dataSize > 0) {
|
||||
theDataBuffer.mBuffers[0].mDataByteSize = (UInt32)dataSize;
|
||||
theDataBuffer.mBuffers[0].mData = _pcmData + _bytesOfRead;
|
||||
frames = readInFrames;
|
||||
ExtAudioFileRead(extRef, (UInt32*)&frames, &theDataBuffer);
|
||||
}
|
||||
|
||||
_bytesOfRead = _dataSize;
|
||||
}
|
||||
else{
|
||||
_queBufferFrames = theFileFormat.mSampleRate * QUEUEBUFFER_TIME_STEP;
|
||||
_queBufferBytes = _queBufferFrames * outputFormat.mBytesPerFrame;
|
||||
|
||||
theDataBuffer.mNumberBuffers = QUEUEBUFFER_NUM;
|
||||
for (int index = 0; index < QUEUEBUFFER_NUM; ++index) {
|
||||
_queBuffers[index] = (char*)malloc(_queBufferBytes);
|
||||
|
||||
theDataBuffer.mBuffers[index].mDataByteSize = _queBufferBytes;
|
||||
theDataBuffer.mBuffers[index].mNumberChannels = outputFormat.mChannelsPerFrame;
|
||||
theDataBuffer.mBuffers[index].mData = _queBuffers[index];
|
||||
}
|
||||
|
||||
frames = _queBufferFrames * QUEUEBUFFER_NUM;
|
||||
ExtAudioFileRead(extRef, (UInt32*)&frames, &theDataBuffer);
|
||||
}
|
||||
|
||||
ExitThread:
|
||||
CFRelease(fileURL);
|
||||
if (extRef)
|
||||
ExtAudioFileDispose(extRef);
|
||||
|
||||
_readDataTaskMutex.unlock();
|
||||
if (_queBufferFrames > 0)
|
||||
_alBufferReady = true;
|
||||
|
||||
invokingCallbacks();
|
||||
}
|
||||
|
||||
void AudioCache::invokingCallbacks()
|
||||
{
|
||||
_callbackMutex.lock();
|
||||
auto count = _callbacks.size();
|
||||
for (size_t index = 0; index < count; ++index) {
|
||||
_callbacks[index]();
|
||||
}
|
||||
_callbacks.clear();
|
||||
_callbackMutex.unlock();
|
||||
}
|
||||
|
||||
void AudioCache::addCallbacks(const std::function<void ()> &callback)
|
||||
{
|
||||
_callbackMutex.lock();
|
||||
if (_alBufferReady) {
|
||||
callback();
|
||||
} else {
|
||||
_callbacks.push_back(callback);
|
||||
}
|
||||
_callbackMutex.unlock();
|
||||
}
|
|
@ -0,0 +1,94 @@
|
|||
/****************************************************************************
|
||||
Copyright (c) 2014 Chukong Technologies Inc.
|
||||
|
||||
http://www.cocos2d-x.org
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in
|
||||
all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
THE SOFTWARE.
|
||||
****************************************************************************/
|
||||
#if CC_TARGET_PLATFORM == CC_PLATFORM_IOS
|
||||
|
||||
#ifndef __AUDIO_ENGINE_INL_H_
|
||||
#define __AUDIO_ENGINE_INL_H_
|
||||
|
||||
#include <unordered_map>
|
||||
|
||||
#include "base/CCRef.h"
|
||||
#include "AudioCache.h"
|
||||
#include "AudioPlayer.h"
|
||||
|
||||
NS_CC_BEGIN
|
||||
|
||||
#define MAX_AUDIOINSTANCES 32
|
||||
|
||||
class AudioEngineThreadPool;
|
||||
|
||||
class AudioEngineImpl : public cocos2d::Ref
|
||||
{
|
||||
public:
|
||||
AudioEngineImpl();
|
||||
~AudioEngineImpl();
|
||||
|
||||
bool init();
|
||||
int play2d(const std::string &fileFullPath ,bool loop ,float volume);
|
||||
void setVolume(int audioID,float volume);
|
||||
void setLoop(int audioID, bool loop);
|
||||
bool pause(int audioID);
|
||||
bool resume(int audioID);
|
||||
bool stop(int audioID);
|
||||
void stopAll();
|
||||
float getDuration(int audioID);
|
||||
float getCurrentTime(int audioID);
|
||||
bool setCurrentTime(int audioID, float time);
|
||||
void setFinishCallback(int audioID, const std::function<void (int, const std::string &)> &callback);
|
||||
|
||||
void uncache(const std::string& filePath);
|
||||
void uncacheAll();
|
||||
|
||||
void update(float dt);
|
||||
|
||||
private:
|
||||
void _play2d(AudioCache *cache, int audioID);
|
||||
|
||||
AudioEngineThreadPool* _threadPool;
|
||||
|
||||
ALuint _alSources[MAX_AUDIOINSTANCES];
|
||||
|
||||
//source,used
|
||||
std::unordered_map<ALuint, bool> _alSourceUsed;
|
||||
|
||||
//filePath,bufferInfo
|
||||
std::unordered_map<std::string, AudioCache> _audioCaches;
|
||||
|
||||
//audioID,AudioInfo
|
||||
std::unordered_map<int, AudioPlayer> _audioPlayers;
|
||||
|
||||
std::mutex _threadMutex;
|
||||
|
||||
std::vector<AudioCache*> _toRemoveCaches;
|
||||
std::vector<int> _toRemoveAudioIDs;
|
||||
|
||||
bool _lazyInitLoop;
|
||||
|
||||
int _currentAudioID;
|
||||
|
||||
};
|
||||
NS_CC_END
|
||||
#endif // __AUDIO_ENGINE_INL_H_
|
||||
#endif
|
||||
|
|
@ -0,0 +1,505 @@
|
|||
/****************************************************************************
|
||||
Copyright (c) 2014 Chukong Technologies Inc.
|
||||
|
||||
http://www.cocos2d-x.org
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in
|
||||
all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
THE SOFTWARE.
|
||||
****************************************************************************/
|
||||
#include "AudioEngine-inl.h"
|
||||
#include "audio/include/AudioEngine.h"
|
||||
|
||||
#import <OpenAL/alc.h>
|
||||
#include "platform/CCFileUtils.h"
|
||||
#include "base/CCDirector.h"
|
||||
#include "base/CCScheduler.h"
|
||||
#include "base/ccUtils.h"
|
||||
|
||||
using namespace cocos2d;
|
||||
|
||||
static ALCdevice *s_ALDevice = nullptr;
|
||||
static ALCcontext *s_ALContext = nullptr;
|
||||
|
||||
static void AudioInterrupionListenerCallback(void* user_data, UInt32 interruption_state)
|
||||
{
|
||||
if(kAudioSessionBeginInterruption == interruption_state){
|
||||
alcMakeContextCurrent(nullptr);
|
||||
}
|
||||
else if (kAudioSessionEndInterruption == interruption_state){
|
||||
AudioSessionSetActive(true);
|
||||
alcMakeContextCurrent(s_ALContext);
|
||||
}
|
||||
}
|
||||
|
||||
namespace cocos2d {
|
||||
class AudioEngineThreadPool
|
||||
{
|
||||
public:
|
||||
AudioEngineThreadPool()
|
||||
: _running(true)
|
||||
, _numThread(6)
|
||||
{
|
||||
_threads.reserve(_numThread);
|
||||
_tasks.reserve(_numThread);
|
||||
|
||||
for (int index = 0; index < _numThread; ++index) {
|
||||
_tasks.push_back(nullptr);
|
||||
_threads.push_back( std::thread( std::bind(&AudioEngineThreadPool::threadFunc,this,index) ) );
|
||||
}
|
||||
}
|
||||
|
||||
void addTask(const std::function<void()> &task){
|
||||
_taskMutex.lock();
|
||||
int targetIndex = -1;
|
||||
for (int index = 0; index < _numThread; ++index) {
|
||||
if (_tasks[index] == nullptr) {
|
||||
targetIndex = index;
|
||||
_tasks[index] = task;
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (targetIndex == -1) {
|
||||
_tasks.push_back(task);
|
||||
_threads.push_back( std::thread( std::bind(&AudioEngineThreadPool::threadFunc,this,_numThread) ) );
|
||||
|
||||
_numThread++;
|
||||
}
|
||||
_taskMutex.unlock();
|
||||
|
||||
_sleepCondition.notify_all();
|
||||
}
|
||||
|
||||
void destroy()
|
||||
{
|
||||
_running = false;
|
||||
_sleepCondition.notify_all();
|
||||
|
||||
for (int index = 0; index < _numThread; ++index) {
|
||||
_threads[index].join();
|
||||
}
|
||||
}
|
||||
|
||||
private:
|
||||
bool _running;
|
||||
std::vector<std::thread> _threads;
|
||||
std::vector< std::function<void ()> > _tasks;
|
||||
|
||||
void threadFunc(int index)
|
||||
{
|
||||
while (_running) {
|
||||
std::function<void ()> task = nullptr;
|
||||
_taskMutex.lock();
|
||||
task = _tasks[index];
|
||||
_taskMutex.unlock();
|
||||
|
||||
if (nullptr == task)
|
||||
{
|
||||
std::unique_lock<std::mutex> lk(_sleepMutex);
|
||||
_sleepCondition.wait(lk);
|
||||
continue;
|
||||
}
|
||||
|
||||
task();
|
||||
|
||||
_taskMutex.lock();
|
||||
_tasks[index] = nullptr;
|
||||
_taskMutex.unlock();
|
||||
}
|
||||
}
|
||||
|
||||
int _numThread;
|
||||
|
||||
std::mutex _taskMutex;
|
||||
std::mutex _sleepMutex;
|
||||
std::condition_variable _sleepCondition;
|
||||
|
||||
};
|
||||
}
|
||||
|
||||
AudioEngineImpl::AudioEngineImpl()
|
||||
: _lazyInitLoop(true)
|
||||
, _currentAudioID(0)
|
||||
, _threadPool(nullptr)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
AudioEngineImpl::~AudioEngineImpl()
|
||||
{
|
||||
if (s_ALContext) {
|
||||
alDeleteSources(MAX_AUDIOINSTANCES, _alSources);
|
||||
|
||||
_audioCaches.clear();
|
||||
|
||||
alcDestroyContext(s_ALContext);
|
||||
}
|
||||
if (s_ALDevice) {
|
||||
alcCloseDevice(s_ALDevice);
|
||||
}
|
||||
if (_threadPool) {
|
||||
_threadPool->destroy();
|
||||
delete _threadPool;
|
||||
}
|
||||
}
|
||||
|
||||
bool AudioEngineImpl::init()
|
||||
{
|
||||
//set up the audio session
|
||||
AudioSessionInitialize(nullptr, nullptr, AudioInterrupionListenerCallback, nullptr);
|
||||
|
||||
bool ret = false;
|
||||
do{
|
||||
s_ALDevice = alcOpenDevice(nullptr);
|
||||
|
||||
if (s_ALDevice) {
|
||||
auto alError = alGetError();
|
||||
s_ALContext = alcCreateContext(s_ALDevice, nullptr);
|
||||
alcMakeContextCurrent(s_ALContext);
|
||||
|
||||
alGenSources(MAX_AUDIOINSTANCES, _alSources);
|
||||
alError = alGetError();
|
||||
if(alError != AL_NO_ERROR)
|
||||
{
|
||||
printf("%s:generating sources fail! error = %x\n", __PRETTY_FUNCTION__, alError);
|
||||
break;
|
||||
}
|
||||
|
||||
for (int i = 0; i < MAX_AUDIOINSTANCES; ++i) {
|
||||
_alSourceUsed[_alSources[i]] = false;
|
||||
}
|
||||
|
||||
_threadPool = new (std::nothrow) AudioEngineThreadPool();
|
||||
ret = true;
|
||||
}
|
||||
}while (false);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
int AudioEngineImpl::play2d(const std::string &filePath ,bool loop ,float volume)
|
||||
{
|
||||
if (s_ALDevice == nullptr) {
|
||||
return AudioEngine::INVAILD_AUDIO_ID;
|
||||
}
|
||||
|
||||
bool sourceFlag = false;
|
||||
ALuint alSource = 0;
|
||||
for (int i = 0; i < MAX_AUDIOINSTANCES; ++i) {
|
||||
alSource = _alSources[i];
|
||||
|
||||
if ( !_alSourceUsed[alSource]) {
|
||||
sourceFlag = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
if(!sourceFlag){
|
||||
return AudioEngine::INVAILD_AUDIO_ID;
|
||||
}
|
||||
|
||||
AudioCache* audioCache = nullptr;
|
||||
auto it = _audioCaches.find(filePath);
|
||||
if (it == _audioCaches.end()) {
|
||||
audioCache = &_audioCaches[filePath];
|
||||
audioCache->_fileFullPath = FileUtils::getInstance()->fullPathForFilename(filePath);
|
||||
|
||||
_threadPool->addTask(std::bind(&AudioCache::readDataTask, audioCache));
|
||||
}
|
||||
else {
|
||||
audioCache = &it->second;
|
||||
}
|
||||
|
||||
auto player = &_audioPlayers[_currentAudioID];
|
||||
player->_alSource = alSource;
|
||||
player->_loop = loop;
|
||||
player->_volume = volume;
|
||||
audioCache->addCallbacks(std::bind(&AudioEngineImpl::_play2d,this,audioCache,_currentAudioID));
|
||||
|
||||
_alSourceUsed[alSource] = true;
|
||||
|
||||
if (_lazyInitLoop) {
|
||||
_lazyInitLoop = false;
|
||||
|
||||
auto scheduler = cocos2d::Director::getInstance()->getScheduler();
|
||||
scheduler->schedule(schedule_selector(AudioEngineImpl::update), this, 0.05f, false);
|
||||
}
|
||||
|
||||
return _currentAudioID++;
|
||||
}
|
||||
|
||||
void AudioEngineImpl::_play2d(AudioCache *cache, int audioID)
|
||||
{
|
||||
if(cache->_alBufferReady){
|
||||
auto playerIt = _audioPlayers.find(audioID);
|
||||
if (playerIt != _audioPlayers.end()) {
|
||||
if (playerIt->second.play2d(cache)) {
|
||||
AudioEngine::_audioIDInfoMap[audioID].state = AudioEngine::AudioState::PLAYING;
|
||||
}
|
||||
else{
|
||||
_threadMutex.lock();
|
||||
_toRemoveAudioIDs.push_back(audioID);
|
||||
_threadMutex.unlock();
|
||||
}
|
||||
}
|
||||
}
|
||||
else {
|
||||
_threadMutex.lock();
|
||||
_toRemoveCaches.push_back(cache);
|
||||
_toRemoveAudioIDs.push_back(audioID);
|
||||
_threadMutex.unlock();
|
||||
}
|
||||
}
|
||||
|
||||
void AudioEngineImpl::setVolume(int audioID,float volume)
|
||||
{
|
||||
auto& player = _audioPlayers[audioID];
|
||||
player._volume = volume;
|
||||
|
||||
if (player._ready) {
|
||||
alSourcef(_audioPlayers[audioID]._alSource, AL_GAIN, volume);
|
||||
|
||||
auto error = alGetError();
|
||||
if (error != AL_NO_ERROR) {
|
||||
printf("%s: audio id = %d, error = %x\n", __PRETTY_FUNCTION__,audioID,error);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void AudioEngineImpl::setLoop(int audioID, bool loop)
|
||||
{
|
||||
auto& player = _audioPlayers[audioID];
|
||||
|
||||
if (player._ready) {
|
||||
if (player._streamingSource) {
|
||||
player.setLoop(loop);
|
||||
} else {
|
||||
if (loop) {
|
||||
alSourcei(player._alSource, AL_LOOPING, AL_TRUE);
|
||||
} else {
|
||||
alSourcei(player._alSource, AL_LOOPING, AL_FALSE);
|
||||
}
|
||||
|
||||
auto error = alGetError();
|
||||
if (error != AL_NO_ERROR) {
|
||||
printf("%s: audio id = %d, error = %x\n", __PRETTY_FUNCTION__,audioID,error);
|
||||
}
|
||||
}
|
||||
}
|
||||
else {
|
||||
player._loop = loop;
|
||||
}
|
||||
}
|
||||
|
||||
bool AudioEngineImpl::pause(int audioID)
|
||||
{
|
||||
bool ret = true;
|
||||
alSourcePause(_audioPlayers[audioID]._alSource);
|
||||
|
||||
auto error = alGetError();
|
||||
if (error != AL_NO_ERROR) {
|
||||
ret = false;
|
||||
printf("%s: audio id = %d, error = %x\n", __PRETTY_FUNCTION__,audioID,error);
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
bool AudioEngineImpl::resume(int audioID)
|
||||
{
|
||||
bool ret = true;
|
||||
alSourcePlay(_audioPlayers[audioID]._alSource);
|
||||
|
||||
auto error = alGetError();
|
||||
if (error != AL_NO_ERROR) {
|
||||
ret = false;
|
||||
printf("%s: audio id = %d, error = %x\n", __PRETTY_FUNCTION__,audioID,error);
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
bool AudioEngineImpl::stop(int audioID)
|
||||
{
|
||||
bool ret = true;
|
||||
auto& player = _audioPlayers[audioID];
|
||||
if (player._ready) {
|
||||
alSourceStop(player._alSource);
|
||||
|
||||
auto error = alGetError();
|
||||
if (error != AL_NO_ERROR) {
|
||||
ret = false;
|
||||
printf("%s: audio id = %d, error = %x\n", __PRETTY_FUNCTION__,audioID,error);
|
||||
}
|
||||
}
|
||||
|
||||
alSourcei(player._alSource, AL_BUFFER, NULL);
|
||||
|
||||
_alSourceUsed[player._alSource] = false;
|
||||
_audioPlayers.erase(audioID);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
void AudioEngineImpl::stopAll()
|
||||
{
|
||||
for(int index = 0; index < MAX_AUDIOINSTANCES; ++index)
|
||||
{
|
||||
alSourceStop(_alSources[index]);
|
||||
alSourcei(_alSources[index], AL_BUFFER, NULL);
|
||||
_alSourceUsed[_alSources[index]] = false;
|
||||
}
|
||||
|
||||
_audioPlayers.clear();
|
||||
}
|
||||
|
||||
float AudioEngineImpl::getDuration(int audioID)
|
||||
{
|
||||
auto& player = _audioPlayers[audioID];
|
||||
if(player._ready){
|
||||
return player._audioCache->_duration;
|
||||
} else {
|
||||
return AudioEngine::TIME_UNKNOWN;
|
||||
}
|
||||
}
|
||||
|
||||
float AudioEngineImpl::getCurrentTime(int audioID)
|
||||
{
|
||||
float ret = 0.0f;
|
||||
auto& player = _audioPlayers[audioID];
|
||||
if(player._ready){
|
||||
if (player._streamingSource) {
|
||||
ret = player.getTime();
|
||||
} else {
|
||||
alGetSourcef(player._alSource, AL_SEC_OFFSET, &ret);
|
||||
|
||||
auto error = alGetError();
|
||||
if (error != AL_NO_ERROR) {
|
||||
printf("%s, audio id:%d,error code:%x", __PRETTY_FUNCTION__,audioID,error);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
bool AudioEngineImpl::setCurrentTime(int audioID, float time)
|
||||
{
|
||||
bool ret = false;
|
||||
auto& player = _audioPlayers[audioID];
|
||||
|
||||
do {
|
||||
if (!player._ready) {
|
||||
break;
|
||||
}
|
||||
|
||||
if (player._streamingSource) {
|
||||
ret = player.setTime(time);
|
||||
break;
|
||||
}
|
||||
else {
|
||||
if (player._audioCache->_bytesOfRead != player._audioCache->_dataSize &&
|
||||
(time * player._audioCache->_sampleRate * player._audioCache->_bytesPerFrame) > player._audioCache->_bytesOfRead) {
|
||||
printf("%s: audio id = %d\n", __PRETTY_FUNCTION__,audioID);
|
||||
break;
|
||||
}
|
||||
|
||||
alSourcef(player._alSource, AL_SEC_OFFSET, time);
|
||||
|
||||
auto error = alGetError();
|
||||
if (error != AL_NO_ERROR) {
|
||||
printf("%s: audio id = %d, error = %x\n", __PRETTY_FUNCTION__,audioID,error);
|
||||
}
|
||||
ret = true;
|
||||
}
|
||||
} while (0);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
void AudioEngineImpl::setFinishCallback(int audioID, const std::function<void (int, const std::string &)> &callback)
|
||||
{
|
||||
_audioPlayers[audioID]._finishCallbak = callback;
|
||||
}
|
||||
|
||||
void AudioEngineImpl::update(float dt)
|
||||
{
|
||||
ALint sourceState;
|
||||
int audioID;
|
||||
|
||||
if (_threadMutex.try_lock()) {
|
||||
size_t removeAudioCount = _toRemoveAudioIDs.size();
|
||||
for (size_t index = 0; index < removeAudioCount; ++index) {
|
||||
audioID = _toRemoveAudioIDs[index];
|
||||
auto playerIt = _audioPlayers.find(audioID);
|
||||
if (playerIt != _audioPlayers.end()) {
|
||||
_alSourceUsed[playerIt->second._alSource] = false;
|
||||
_audioPlayers.erase(audioID);
|
||||
AudioEngine::remove(audioID);
|
||||
}
|
||||
}
|
||||
size_t removeCacheCount = _toRemoveCaches.size();
|
||||
for (size_t index = 0; index < removeCacheCount; ++index) {
|
||||
auto itEnd = _audioCaches.end();
|
||||
for (auto it = _audioCaches.begin(); it != itEnd; ++it) {
|
||||
if (&it->second == _toRemoveCaches[index]) {
|
||||
_audioCaches.erase(it);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
_threadMutex.unlock();
|
||||
}
|
||||
|
||||
for (auto it = _audioPlayers.begin(); it != _audioPlayers.end(); ) {
|
||||
audioID = it->first;
|
||||
auto& player = it->second;
|
||||
alGetSourcei(player._alSource, AL_SOURCE_STATE, &sourceState);
|
||||
|
||||
if (player._ready && sourceState == AL_STOPPED) {
|
||||
_alSourceUsed[player._alSource] = false;
|
||||
auto& audioInfo = AudioEngine::_audioIDInfoMap[audioID];
|
||||
if (player._finishCallbak) {
|
||||
player._finishCallbak(audioID, *audioInfo.filePath);
|
||||
}
|
||||
|
||||
AudioEngine::remove(audioID);
|
||||
|
||||
it = _audioPlayers.erase(it);
|
||||
}
|
||||
else{
|
||||
++it;
|
||||
}
|
||||
}
|
||||
|
||||
if(_audioPlayers.empty()){
|
||||
_lazyInitLoop = true;
|
||||
|
||||
auto scheduler = cocos2d::Director::getInstance()->getScheduler();
|
||||
scheduler->unschedule(schedule_selector(AudioEngineImpl::update), this);
|
||||
}
|
||||
}
|
||||
|
||||
void AudioEngineImpl::uncache(const std::string &filePath)
|
||||
{
|
||||
auto fileFullPath = FileUtils::getInstance()->fullPathForFilename(filePath);
|
||||
_audioCaches.erase(fileFullPath);
|
||||
}
|
||||
|
||||
void AudioEngineImpl::uncacheAll()
|
||||
{
|
||||
_audioCaches.clear();
|
||||
}
|
|
@ -0,0 +1,76 @@
|
|||
/****************************************************************************
|
||||
Copyright (c) 2014 Chukong Technologies Inc.
|
||||
|
||||
http://www.cocos2d-x.org
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in
|
||||
all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
THE SOFTWARE.
|
||||
****************************************************************************/
|
||||
#if CC_TARGET_PLATFORM == CC_PLATFORM_IOS
|
||||
|
||||
#ifndef __AUDIO_PLAYER_H_
|
||||
#define __AUDIO_PLAYER_H_
|
||||
|
||||
#import <OpenAL/al.h>
|
||||
#include <string>
|
||||
#include <mutex>
|
||||
#include "CCPlatformMacros.h"
|
||||
|
||||
NS_CC_BEGIN
|
||||
class AudioCache;
|
||||
class AudioEngineImpl;
|
||||
|
||||
class AudioPlayer
|
||||
{
|
||||
public:
|
||||
AudioPlayer();
|
||||
~AudioPlayer();
|
||||
|
||||
//queue buffer related stuff
|
||||
bool setTime(float time);
|
||||
float getTime() { return _currTime;}
|
||||
bool setLoop(bool loop);
|
||||
|
||||
private:
|
||||
void rotateBufferThread(int offsetFrame);
|
||||
bool play2d(AudioCache* cache);
|
||||
|
||||
AudioCache* _audioCache;
|
||||
|
||||
float _volume;
|
||||
bool _loop;
|
||||
std::function<void (int, const std::string &)> _finishCallbak;
|
||||
|
||||
bool _ready;
|
||||
ALuint _alSource;
|
||||
|
||||
//play by circular buffer
|
||||
float _currTime;
|
||||
bool _streamingSource;
|
||||
ALuint _bufferIds[3];
|
||||
std::thread _rotateBufferThread;
|
||||
std::timed_mutex _timeMtx;
|
||||
bool _exitThread;
|
||||
bool _timeDirty;
|
||||
|
||||
friend class AudioEngineImpl;
|
||||
};
|
||||
NS_CC_END
|
||||
#endif // __AUDIO_PLAYER_H_
|
||||
#endif
|
||||
|
|
@ -0,0 +1,214 @@
|
|||
/****************************************************************************
|
||||
Copyright (c) 2014 Chukong Technologies Inc.
|
||||
|
||||
http://www.cocos2d-x.org
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in
|
||||
all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
THE SOFTWARE.
|
||||
****************************************************************************/
|
||||
#include "AudioPlayer.h"
|
||||
#include "AudioCache.h"
|
||||
#include "platform/CCFileUtils.h"
|
||||
#import <AudioToolbox/ExtendedAudioFile.h>
|
||||
|
||||
using namespace cocos2d;
|
||||
|
||||
AudioPlayer::AudioPlayer()
|
||||
: _exitThread(false)
|
||||
, _timeDirty(false)
|
||||
, _streamingSource(false)
|
||||
, _currTime(0.0f)
|
||||
, _finishCallbak(nullptr)
|
||||
, _ready(false)
|
||||
, _audioCache(nullptr)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
AudioPlayer::~AudioPlayer()
|
||||
{
|
||||
_exitThread = true;
|
||||
if (_audioCache && _audioCache->_queBufferFrames > 0) {
|
||||
_timeMtx.unlock();
|
||||
if (_rotateBufferThread.joinable()) {
|
||||
_rotateBufferThread.join();
|
||||
}
|
||||
alDeleteBuffers(3, _bufferIds);
|
||||
}
|
||||
}
|
||||
|
||||
bool AudioPlayer::play2d(AudioCache* cache)
|
||||
{
|
||||
if (!cache->_alBufferReady) {
|
||||
return false;
|
||||
}
|
||||
_audioCache = cache;
|
||||
|
||||
alSourcei(_alSource, AL_BUFFER, NULL);
|
||||
alSourcef(_alSource, AL_PITCH, 1.0f);
|
||||
alSourcef(_alSource, AL_GAIN, _volume);
|
||||
|
||||
if (_audioCache->_queBufferFrames == 0) {
|
||||
if (_loop) {
|
||||
alSourcei(_alSource, AL_LOOPING, AL_TRUE);
|
||||
}
|
||||
else {
|
||||
alSourcei(_alSource, AL_LOOPING, AL_FALSE);
|
||||
}
|
||||
alSourcei(_alSource, AL_BUFFER, _audioCache->_alBufferId);
|
||||
|
||||
} else {
|
||||
_streamingSource = true;
|
||||
|
||||
auto alError = alGetError();
|
||||
alGenBuffers(3, _bufferIds);
|
||||
alError = alGetError();
|
||||
if (alError == AL_NO_ERROR) {
|
||||
for (int index = 0; index < QUEUEBUFFER_NUM; ++index) {
|
||||
alBufferData(_bufferIds[index], _audioCache->_format, _audioCache->_queBuffers[index], _audioCache->_queBufferBytes, _audioCache->_sampleRate);
|
||||
}
|
||||
alSourcei(_alSource, AL_BUFFER, NULL);
|
||||
alSourceQueueBuffers(_alSource, QUEUEBUFFER_NUM, _bufferIds);
|
||||
|
||||
_timeMtx.lock();
|
||||
_rotateBufferThread = std::thread(&AudioPlayer::rotateBufferThread,this, _audioCache->_queBufferFrames * QUEUEBUFFER_NUM + 1);
|
||||
}
|
||||
else {
|
||||
printf("%s:alGenBuffers error code:%x", __PRETTY_FUNCTION__,alError);
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
alSourcePlay(_alSource);
|
||||
_ready = true;
|
||||
auto alError = alGetError();
|
||||
|
||||
if (alError != AL_NO_ERROR) {
|
||||
printf("%s:alSourcePlay error code:%x\n", __PRETTY_FUNCTION__,alError);
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
void AudioPlayer::rotateBufferThread(int offsetFrame)
|
||||
{
|
||||
printf("%s start\n",__PRETTY_FUNCTION__);
|
||||
|
||||
ALint sourceState;
|
||||
ALint bufferProcessed = 0;
|
||||
ExtAudioFileRef extRef = nullptr;
|
||||
|
||||
auto fileURL = (CFURLRef)[[NSURL fileURLWithPath:[NSString stringWithCString:_audioCache->_fileFullPath.c_str() encoding:[NSString defaultCStringEncoding]]] retain];
|
||||
char* tmpBuffer = (char*)malloc(_audioCache->_queBufferBytes);
|
||||
auto frames = _audioCache->_queBufferFrames;
|
||||
|
||||
auto error = ExtAudioFileOpenURL(fileURL, &extRef);
|
||||
if(error) {
|
||||
printf("%s: ExtAudioFileOpenURL FAILED, Error = %d\n", __PRETTY_FUNCTION__, error);
|
||||
goto ExitBufferThread;
|
||||
}
|
||||
|
||||
error = ExtAudioFileSetProperty(extRef, kExtAudioFileProperty_ClientDataFormat, sizeof(_audioCache->outputFormat), &_audioCache->outputFormat);
|
||||
AudioBufferList theDataBuffer;
|
||||
theDataBuffer.mNumberBuffers = 1;
|
||||
theDataBuffer.mBuffers[0].mData = tmpBuffer;
|
||||
theDataBuffer.mBuffers[0].mDataByteSize = _audioCache->_queBufferBytes;
|
||||
theDataBuffer.mBuffers[0].mNumberChannels = _audioCache->outputFormat.mChannelsPerFrame;
|
||||
|
||||
if (offsetFrame != 0) {
|
||||
ExtAudioFileSeek(extRef, offsetFrame);
|
||||
}
|
||||
|
||||
while (!_exitThread) {
|
||||
alGetSourcei(_alSource, AL_SOURCE_STATE, &sourceState);
|
||||
if (sourceState == AL_PLAYING) {
|
||||
alGetSourcei(_alSource, AL_BUFFERS_PROCESSED, &bufferProcessed);
|
||||
while (bufferProcessed > 0) {
|
||||
bufferProcessed--;
|
||||
if (_timeDirty) {
|
||||
_timeDirty = false;
|
||||
offsetFrame = _currTime * _audioCache->outputFormat.mSampleRate;
|
||||
ExtAudioFileSeek(extRef, offsetFrame);
|
||||
}
|
||||
else {
|
||||
_currTime += QUEUEBUFFER_TIME_STEP;
|
||||
if (_currTime > _audioCache->_duration) {
|
||||
if (_loop) {
|
||||
_currTime = 0.0f;
|
||||
} else {
|
||||
_currTime = _audioCache->_duration;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
frames = _audioCache->_queBufferFrames;
|
||||
ExtAudioFileRead(extRef, (UInt32*)&frames, &theDataBuffer);
|
||||
if (frames <= 0) {
|
||||
if (_loop) {
|
||||
ExtAudioFileSeek(extRef, 0);
|
||||
frames = _audioCache->_queBufferFrames;
|
||||
theDataBuffer.mBuffers[0].mDataByteSize = _audioCache->_queBufferBytes;
|
||||
ExtAudioFileRead(extRef, (UInt32*)&frames, &theDataBuffer);
|
||||
} else {
|
||||
_exitThread = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
ALuint bid;
|
||||
alSourceUnqueueBuffers(_alSource, 1, &bid);
|
||||
alBufferData(bid, _audioCache->_format, tmpBuffer, frames * _audioCache->outputFormat.mBytesPerFrame, _audioCache->_sampleRate);
|
||||
alSourceQueueBuffers(_alSource, 1, &bid);
|
||||
}
|
||||
}
|
||||
|
||||
_timeMtx.try_lock_for(std::chrono::milliseconds(50));
|
||||
}
|
||||
|
||||
ExitBufferThread:
|
||||
CFRelease(fileURL);
|
||||
// Dispose the ExtAudioFileRef, it is no longer needed
|
||||
if (extRef){
|
||||
ExtAudioFileDispose(extRef);
|
||||
}
|
||||
free(tmpBuffer);
|
||||
printf("%s: end\n",__PRETTY_FUNCTION__);
|
||||
}
|
||||
|
||||
bool AudioPlayer::setLoop(bool loop)
|
||||
{
|
||||
if (!_exitThread ) {
|
||||
_loop = loop;
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
bool AudioPlayer::setTime(float time)
|
||||
{
|
||||
if (!_exitThread && time >= 0.0f && time < _audioCache->_duration) {
|
||||
|
||||
_currTime = time;
|
||||
_timeDirty = true;
|
||||
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
|
@ -486,8 +486,9 @@ void Armature::visit(cocos2d::Renderer *renderer, const Mat4 &parentTransform, u
|
|||
sortAllChildren();
|
||||
draw(renderer, _modelViewTransform, flags);
|
||||
|
||||
// reset for next frame
|
||||
_orderOfArrival = 0;
|
||||
// FIX ME: Why need to set _orderOfArrival to 0??
|
||||
// Please refer to https://github.com/cocos2d/cocos2d-x/pull/6920
|
||||
// setOrderOfArrival(0);
|
||||
|
||||
director->popMatrix(MATRIX_STACK_TYPE::MATRIX_STACK_MODELVIEW);
|
||||
}
|
||||
|
|
|
@ -124,8 +124,9 @@ void BatchNode::visit(Renderer *renderer, const Mat4 &parentTransform, uint32_t
|
|||
sortAllChildren();
|
||||
draw(renderer, _modelViewTransform, flags);
|
||||
|
||||
// reset for next frame
|
||||
_orderOfArrival = 0;
|
||||
// FIX ME: Why need to set _orderOfArrival to 0??
|
||||
// Please refer to https://github.com/cocos2d/cocos2d-x/pull/6920
|
||||
// setOrderOfArrival(0);
|
||||
|
||||
director->popMatrix(MATRIX_STACK_TYPE::MATRIX_STACK_MODELVIEW);
|
||||
}
|
||||
|
|
|
@ -414,8 +414,11 @@ void Mat4::add(float scalar)
|
|||
void Mat4::add(float scalar, Mat4* dst)
|
||||
{
|
||||
GP_ASSERT(dst);
|
||||
|
||||
#ifdef __SSE__
|
||||
MathUtil::addMatrix(col, scalar, dst->col);
|
||||
#else
|
||||
MathUtil::addMatrix(m, scalar, dst->m);
|
||||
#endif
|
||||
}
|
||||
|
||||
void Mat4::add(const Mat4& mat)
|
||||
|
@ -426,8 +429,11 @@ void Mat4::add(const Mat4& mat)
|
|||
void Mat4::add(const Mat4& m1, const Mat4& m2, Mat4* dst)
|
||||
{
|
||||
GP_ASSERT(dst);
|
||||
|
||||
#ifdef __SSE__
|
||||
MathUtil::addMatrix(m1.col, m2.col, dst->col);
|
||||
#else
|
||||
MathUtil::addMatrix(m1.m, m2.m, dst->m);
|
||||
#endif
|
||||
}
|
||||
|
||||
bool Mat4::decompose(Vec3* scale, Quaternion* rotation, Vec3* translation) const
|
||||
|
@ -700,8 +706,11 @@ void Mat4::multiply(float scalar, Mat4* dst) const
|
|||
void Mat4::multiply(const Mat4& m, float scalar, Mat4* dst)
|
||||
{
|
||||
GP_ASSERT(dst);
|
||||
|
||||
#ifdef __SSE__
|
||||
MathUtil::multiplyMatrix(m.col, scalar, dst->col);
|
||||
#else
|
||||
MathUtil::multiplyMatrix(m.m, scalar, dst->m);
|
||||
#endif
|
||||
}
|
||||
|
||||
void Mat4::multiply(const Mat4& mat)
|
||||
|
@ -712,13 +721,20 @@ void Mat4::multiply(const Mat4& mat)
|
|||
void Mat4::multiply(const Mat4& m1, const Mat4& m2, Mat4* dst)
|
||||
{
|
||||
GP_ASSERT(dst);
|
||||
|
||||
#ifdef __SSE__
|
||||
MathUtil::multiplyMatrix(m1.col, m2.col, dst->col);
|
||||
#else
|
||||
MathUtil::multiplyMatrix(m1.m, m2.m, dst->m);
|
||||
#endif
|
||||
}
|
||||
|
||||
void Mat4::negate()
|
||||
{
|
||||
#ifdef __SSE__
|
||||
MathUtil::negateMatrix(col, col);
|
||||
#else
|
||||
MathUtil::negateMatrix(m, m);
|
||||
#endif
|
||||
}
|
||||
|
||||
Mat4 Mat4::getNegated() const
|
||||
|
@ -870,8 +886,11 @@ void Mat4::subtract(const Mat4& mat)
|
|||
void Mat4::subtract(const Mat4& m1, const Mat4& m2, Mat4* dst)
|
||||
{
|
||||
GP_ASSERT(dst);
|
||||
|
||||
#ifdef __SSE__
|
||||
MathUtil::subtractMatrix(m1.col, m2.col, dst->col);
|
||||
#else
|
||||
MathUtil::subtractMatrix(m1.m, m2.m, dst->m);
|
||||
#endif
|
||||
}
|
||||
|
||||
void Mat4::transformPoint(Vec3* point) const
|
||||
|
@ -912,8 +931,11 @@ void Mat4::transformVector(Vec4* vector) const
|
|||
void Mat4::transformVector(const Vec4& vector, Vec4* dst) const
|
||||
{
|
||||
GP_ASSERT(dst);
|
||||
|
||||
#ifdef __SSE__
|
||||
MathUtil::transformVec4(col, vector.v, dst->v);
|
||||
#else
|
||||
MathUtil::transformVec4(m, (const float*) &vector, (float*)dst);
|
||||
#endif
|
||||
}
|
||||
|
||||
void Mat4::translate(float x, float y, float z)
|
||||
|
@ -940,7 +962,11 @@ void Mat4::translate(const Vec3& t, Mat4* dst) const
|
|||
|
||||
void Mat4::transpose()
|
||||
{
|
||||
#ifdef __SSE__
|
||||
MathUtil::transposeMatrix(col, col);
|
||||
#else
|
||||
MathUtil::transposeMatrix(m, m);
|
||||
#endif
|
||||
}
|
||||
|
||||
Mat4 Mat4::getTransposed() const
|
||||
|
|
|
@ -24,6 +24,10 @@
|
|||
#include "math/Vec3.h"
|
||||
#include "math/Vec4.h"
|
||||
|
||||
#ifdef __SSE__
|
||||
#include <xmmintrin.h>
|
||||
#endif
|
||||
|
||||
NS_CC_MATH_BEGIN
|
||||
|
||||
//class Plane;
|
||||
|
@ -77,7 +81,14 @@ public:
|
|||
/**
|
||||
* Stores the columns of this 4x4 matrix.
|
||||
* */
|
||||
#ifdef __SSE__
|
||||
union {
|
||||
__m128 col[4];
|
||||
float m[16];
|
||||
};
|
||||
#else
|
||||
float m[16];
|
||||
#endif
|
||||
|
||||
/**
|
||||
* Constructs a matrix initialized to the identity matrix:
|
||||
|
|
|
@ -21,6 +21,10 @@
|
|||
#ifndef MATHUTIL_H_
|
||||
#define MATHUTIL_H_
|
||||
|
||||
#ifdef __SSE__
|
||||
#include <xmmintrin.h>
|
||||
#endif
|
||||
|
||||
#include "CCMathBase.h"
|
||||
|
||||
NS_CC_MATH_BEGIN
|
||||
|
@ -67,7 +71,23 @@ public:
|
|||
static void smooth(float* x, float target, float elapsedTime, float riseTime, float fallTime);
|
||||
|
||||
private:
|
||||
|
||||
#ifdef __SSE__
|
||||
inline static void addMatrix(const __m128 m[4], float scalar, __m128 dst[4]);
|
||||
|
||||
inline static void addMatrix(const __m128 m1[4], const __m128 m2[4], __m128 dst[4]);
|
||||
|
||||
inline static void subtractMatrix(const __m128 m1[4], const __m128 m2[4], __m128 dst[4]);
|
||||
|
||||
inline static void multiplyMatrix(const __m128 m[4], float scalar, __m128 dst[4]);
|
||||
|
||||
inline static void multiplyMatrix(const __m128 m1[4], const __m128 m2[4], __m128 dst[4]);
|
||||
|
||||
inline static void negateMatrix(const __m128 m[4], __m128 dst[4]);
|
||||
|
||||
inline static void transposeMatrix(const __m128 m[4], __m128 dst[4]);
|
||||
|
||||
inline static void transformVec4(const __m128 m[4], const __m128& v, __m128& dst);
|
||||
#endif
|
||||
inline static void addMatrix(const float* m, float scalar, float* dst);
|
||||
|
||||
inline static void addMatrix(const float* m1, const float* m2, float* dst);
|
||||
|
@ -99,6 +119,9 @@ NS_CC_MATH_END
|
|||
#include "MathUtilNeon.inl"
|
||||
#else
|
||||
#include "MathUtil.inl"
|
||||
#if defined(__SSE__)
|
||||
#include "MathUtilSSE.inl"
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#endif
|
||||
|
|
|
@ -0,0 +1,152 @@
|
|||
NS_CC_MATH_BEGIN
|
||||
|
||||
inline void MathUtil::addMatrix(const __m128 m[4], float scalar, __m128 dst[4])
|
||||
{
|
||||
__m128 s = _mm_set1_ps(scalar);
|
||||
dst[0] = _mm_add_ps(m[0], s);
|
||||
dst[1] = _mm_add_ps(m[1], s);
|
||||
dst[2] = _mm_add_ps(m[2], s);
|
||||
dst[3] = _mm_add_ps(m[3], s);
|
||||
}
|
||||
|
||||
inline void MathUtil::addMatrix(const __m128 m1[4], const __m128 m2[4], __m128 dst[4])
|
||||
{
|
||||
dst[0] = _mm_add_ps(m1[0], m2[0]);
|
||||
dst[1] = _mm_add_ps(m1[1], m2[1]);
|
||||
dst[2] = _mm_add_ps(m1[2], m2[2]);
|
||||
dst[3] = _mm_add_ps(m1[3], m2[3]);
|
||||
}
|
||||
|
||||
inline void MathUtil::subtractMatrix(const __m128 m1[4], const __m128 m2[4], __m128 dst[4])
|
||||
{
|
||||
dst[0] = _mm_sub_ps(m1[0], m2[0]);
|
||||
dst[1] = _mm_sub_ps(m1[1], m2[1]);
|
||||
dst[2] = _mm_sub_ps(m1[2], m2[2]);
|
||||
dst[3] = _mm_sub_ps(m1[3], m2[3]);
|
||||
}
|
||||
|
||||
inline void MathUtil::multiplyMatrix(const __m128 m[4], float scalar, __m128 dst[4])
|
||||
{
|
||||
__m128 s = _mm_set1_ps(scalar);
|
||||
dst[0] = _mm_mul_ps(m[0], s);
|
||||
dst[1] = _mm_mul_ps(m[1], s);
|
||||
dst[2] = _mm_mul_ps(m[2], s);
|
||||
dst[3] = _mm_mul_ps(m[3], s);
|
||||
}
|
||||
|
||||
inline void MathUtil::multiplyMatrix(const __m128 m1[4], const __m128 m2[4], __m128 dst[4])
|
||||
{
|
||||
__m128 dst0, dst1, dst2, dst3;
|
||||
{
|
||||
__m128 e0 = _mm_shuffle_ps(m2[0], m2[0], _MM_SHUFFLE(0, 0, 0, 0));
|
||||
__m128 e1 = _mm_shuffle_ps(m2[0], m2[0], _MM_SHUFFLE(1, 1, 1, 1));
|
||||
__m128 e2 = _mm_shuffle_ps(m2[0], m2[0], _MM_SHUFFLE(2, 2, 2, 2));
|
||||
__m128 e3 = _mm_shuffle_ps(m2[0], m2[0], _MM_SHUFFLE(3, 3, 3, 3));
|
||||
|
||||
__m128 v0 = _mm_mul_ps(m1[0], e0);
|
||||
__m128 v1 = _mm_mul_ps(m1[1], e1);
|
||||
__m128 v2 = _mm_mul_ps(m1[2], e2);
|
||||
__m128 v3 = _mm_mul_ps(m1[3], e3);
|
||||
|
||||
__m128 a0 = _mm_add_ps(v0, v1);
|
||||
__m128 a1 = _mm_add_ps(v2, v3);
|
||||
__m128 a2 = _mm_add_ps(a0, a1);
|
||||
|
||||
dst0 = a2;
|
||||
}
|
||||
|
||||
{
|
||||
__m128 e0 = _mm_shuffle_ps(m2[1], m2[1], _MM_SHUFFLE(0, 0, 0, 0));
|
||||
__m128 e1 = _mm_shuffle_ps(m2[1], m2[1], _MM_SHUFFLE(1, 1, 1, 1));
|
||||
__m128 e2 = _mm_shuffle_ps(m2[1], m2[1], _MM_SHUFFLE(2, 2, 2, 2));
|
||||
__m128 e3 = _mm_shuffle_ps(m2[1], m2[1], _MM_SHUFFLE(3, 3, 3, 3));
|
||||
|
||||
__m128 v0 = _mm_mul_ps(m1[0], e0);
|
||||
__m128 v1 = _mm_mul_ps(m1[1], e1);
|
||||
__m128 v2 = _mm_mul_ps(m1[2], e2);
|
||||
__m128 v3 = _mm_mul_ps(m1[3], e3);
|
||||
|
||||
__m128 a0 = _mm_add_ps(v0, v1);
|
||||
__m128 a1 = _mm_add_ps(v2, v3);
|
||||
__m128 a2 = _mm_add_ps(a0, a1);
|
||||
|
||||
dst1 = a2;
|
||||
}
|
||||
|
||||
{
|
||||
__m128 e0 = _mm_shuffle_ps(m2[2], m2[2], _MM_SHUFFLE(0, 0, 0, 0));
|
||||
__m128 e1 = _mm_shuffle_ps(m2[2], m2[2], _MM_SHUFFLE(1, 1, 1, 1));
|
||||
__m128 e2 = _mm_shuffle_ps(m2[2], m2[2], _MM_SHUFFLE(2, 2, 2, 2));
|
||||
__m128 e3 = _mm_shuffle_ps(m2[2], m2[2], _MM_SHUFFLE(3, 3, 3, 3));
|
||||
|
||||
__m128 v0 = _mm_mul_ps(m1[0], e0);
|
||||
__m128 v1 = _mm_mul_ps(m1[1], e1);
|
||||
__m128 v2 = _mm_mul_ps(m1[2], e2);
|
||||
__m128 v3 = _mm_mul_ps(m1[3], e3);
|
||||
|
||||
__m128 a0 = _mm_add_ps(v0, v1);
|
||||
__m128 a1 = _mm_add_ps(v2, v3);
|
||||
__m128 a2 = _mm_add_ps(a0, a1);
|
||||
|
||||
dst2 = a2;
|
||||
}
|
||||
|
||||
{
|
||||
__m128 e0 = _mm_shuffle_ps(m2[3], m2[3], _MM_SHUFFLE(0, 0, 0, 0));
|
||||
__m128 e1 = _mm_shuffle_ps(m2[3], m2[3], _MM_SHUFFLE(1, 1, 1, 1));
|
||||
__m128 e2 = _mm_shuffle_ps(m2[3], m2[3], _MM_SHUFFLE(2, 2, 2, 2));
|
||||
__m128 e3 = _mm_shuffle_ps(m2[3], m2[3], _MM_SHUFFLE(3, 3, 3, 3));
|
||||
|
||||
__m128 v0 = _mm_mul_ps(m1[0], e0);
|
||||
__m128 v1 = _mm_mul_ps(m1[1], e1);
|
||||
__m128 v2 = _mm_mul_ps(m1[2], e2);
|
||||
__m128 v3 = _mm_mul_ps(m1[3], e3);
|
||||
|
||||
__m128 a0 = _mm_add_ps(v0, v1);
|
||||
__m128 a1 = _mm_add_ps(v2, v3);
|
||||
__m128 a2 = _mm_add_ps(a0, a1);
|
||||
|
||||
dst3 = a2;
|
||||
}
|
||||
dst[0] = dst0;
|
||||
dst[1] = dst1;
|
||||
dst[2] = dst2;
|
||||
dst[3] = dst3;
|
||||
}
|
||||
|
||||
inline void MathUtil::negateMatrix(const __m128 m[4], __m128 dst[4])
|
||||
{
|
||||
__m128 z = _mm_setzero_ps();
|
||||
dst[0] = _mm_sub_ps(z, m[0]);
|
||||
dst[1] = _mm_sub_ps(z, m[1]);
|
||||
dst[2] = _mm_sub_ps(z, m[2]);
|
||||
dst[3] = _mm_sub_ps(z, m[3]);
|
||||
}
|
||||
|
||||
inline void MathUtil::transposeMatrix(const __m128 m[4], __m128 dst[4])
|
||||
{
|
||||
__m128 tmp0 = _mm_shuffle_ps(m[0], m[1], 0x44);
|
||||
__m128 tmp2 = _mm_shuffle_ps(m[0], m[1], 0xEE);
|
||||
__m128 tmp1 = _mm_shuffle_ps(m[2], m[3], 0x44);
|
||||
__m128 tmp3 = _mm_shuffle_ps(m[2], m[3], 0xEE);
|
||||
|
||||
dst[0] = _mm_shuffle_ps(tmp0, tmp1, 0x88);
|
||||
dst[1] = _mm_shuffle_ps(tmp0, tmp1, 0xDD);
|
||||
dst[2] = _mm_shuffle_ps(tmp2, tmp3, 0x88);
|
||||
dst[3] = _mm_shuffle_ps(tmp2, tmp3, 0xDD);
|
||||
}
|
||||
|
||||
inline void MathUtil::transformVec4(const __m128 m[4], const __m128& v, __m128& dst)
|
||||
{
|
||||
__m128 col1 = _mm_shuffle_ps(v, v, _MM_SHUFFLE(0, 0, 0, 0));
|
||||
__m128 col2 = _mm_shuffle_ps(v, v, _MM_SHUFFLE(1, 1, 1, 1));
|
||||
__m128 col3 = _mm_shuffle_ps(v, v, _MM_SHUFFLE(2, 2, 2, 2));
|
||||
__m128 col4 = _mm_shuffle_ps(v, v, _MM_SHUFFLE(3, 3, 3, 3));
|
||||
|
||||
dst = _mm_add_ps(
|
||||
_mm_add_ps(_mm_mul_ps(m[0], col1), _mm_mul_ps(m[1], col2)),
|
||||
_mm_add_ps(_mm_mul_ps(m[2], col3), _mm_mul_ps(m[3], col4))
|
||||
);
|
||||
}
|
||||
|
||||
NS_CC_MATH_END
|
|
@ -21,6 +21,10 @@
|
|||
#ifndef MATH_VEC4_H
|
||||
#define MATH_VEC4_H
|
||||
|
||||
#ifdef __SSE__
|
||||
#include <xmmintrin.h>
|
||||
#endif
|
||||
|
||||
#include "math/CCMathBase.h"
|
||||
|
||||
NS_CC_MATH_BEGIN
|
||||
|
@ -33,7 +37,17 @@ class Mat4;
|
|||
class CC_DLL Vec4
|
||||
{
|
||||
public:
|
||||
|
||||
#ifdef __SSE__
|
||||
union {
|
||||
struct {
|
||||
float x;
|
||||
float y;
|
||||
float z;
|
||||
float w;
|
||||
};
|
||||
__m128 v;
|
||||
};
|
||||
#else
|
||||
/**
|
||||
* The x-coordinate.
|
||||
*/
|
||||
|
@ -53,7 +67,7 @@ public:
|
|||
* The w-coordinate.
|
||||
*/
|
||||
float w;
|
||||
|
||||
#endif
|
||||
/**
|
||||
* Constructs a new vector initialized to all zeros.
|
||||
*/
|
||||
|
|
|
@ -8511,6 +8511,50 @@ int lua_cocos2dx_extension_ScrollView_setMaxScale(lua_State* tolua_S)
|
|||
|
||||
return 0;
|
||||
}
|
||||
int lua_cocos2dx_extension_ScrollView_hasVisibleParents(lua_State* tolua_S)
|
||||
{
|
||||
int argc = 0;
|
||||
cocos2d::extension::ScrollView* cobj = nullptr;
|
||||
bool ok = true;
|
||||
|
||||
#if COCOS2D_DEBUG >= 1
|
||||
tolua_Error tolua_err;
|
||||
#endif
|
||||
|
||||
|
||||
#if COCOS2D_DEBUG >= 1
|
||||
if (!tolua_isusertype(tolua_S,1,"cc.ScrollView",0,&tolua_err)) goto tolua_lerror;
|
||||
#endif
|
||||
|
||||
cobj = (cocos2d::extension::ScrollView*)tolua_tousertype(tolua_S,1,0);
|
||||
|
||||
#if COCOS2D_DEBUG >= 1
|
||||
if (!cobj)
|
||||
{
|
||||
tolua_error(tolua_S,"invalid 'cobj' in function 'lua_cocos2dx_extension_ScrollView_hasVisibleParents'", nullptr);
|
||||
return 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
argc = lua_gettop(tolua_S)-1;
|
||||
if (argc == 0)
|
||||
{
|
||||
if(!ok)
|
||||
return 0;
|
||||
bool ret = cobj->hasVisibleParents();
|
||||
tolua_pushboolean(tolua_S,(bool)ret);
|
||||
return 1;
|
||||
}
|
||||
CCLOG("%s has wrong number of arguments: %d, was expecting %d \n", "cc.ScrollView:hasVisibleParents",argc, 0);
|
||||
return 0;
|
||||
|
||||
#if COCOS2D_DEBUG >= 1
|
||||
tolua_lerror:
|
||||
tolua_error(tolua_S,"#ferror in function 'lua_cocos2dx_extension_ScrollView_hasVisibleParents'.",&tolua_err);
|
||||
#endif
|
||||
|
||||
return 0;
|
||||
}
|
||||
int lua_cocos2dx_extension_ScrollView_getDirection(lua_State* tolua_S)
|
||||
{
|
||||
int argc = 0;
|
||||
|
@ -9937,6 +9981,7 @@ int lua_register_cocos2dx_extension_ScrollView(lua_State* tolua_S)
|
|||
tolua_function(tolua_S,"setZoomScaleInDuration",lua_cocos2dx_extension_ScrollView_setZoomScaleInDuration);
|
||||
tolua_function(tolua_S,"updateTweenAction",lua_cocos2dx_extension_ScrollView_updateTweenAction);
|
||||
tolua_function(tolua_S,"setMaxScale",lua_cocos2dx_extension_ScrollView_setMaxScale);
|
||||
tolua_function(tolua_S,"hasVisibleParents",lua_cocos2dx_extension_ScrollView_hasVisibleParents);
|
||||
tolua_function(tolua_S,"getDirection",lua_cocos2dx_extension_ScrollView_getDirection);
|
||||
tolua_function(tolua_S,"getContainer",lua_cocos2dx_extension_ScrollView_getContainer);
|
||||
tolua_function(tolua_S,"setMinScale",lua_cocos2dx_extension_ScrollView_setMinScale);
|
||||
|
|
|
@ -262,6 +262,7 @@ int register_all_cocos2dx_extension(lua_State* tolua_S);
|
|||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
#endif // __cocos2dx_extension_h__
|
||||
|
|
|
@ -871,7 +871,7 @@
|
|||
1551A336158F2AB200E66CFE /* Project object */ = {
|
||||
isa = PBXProject;
|
||||
attributes = {
|
||||
LastUpgradeCheck = 0510;
|
||||
LastUpgradeCheck = 0600;
|
||||
ORGANIZATIONNAME = "";
|
||||
};
|
||||
buildConfigurationList = 1551A339158F2AB200E66CFE /* Build configuration list for PBXProject "cocos2d_lua_bindings" */;
|
||||
|
@ -1107,7 +1107,7 @@
|
|||
isa = XCBuildConfiguration;
|
||||
buildSettings = {
|
||||
ALWAYS_SEARCH_USER_PATHS = YES;
|
||||
ARCHS = "$(ARCHS_STANDARD_64_BIT)";
|
||||
COMBINE_HIDPI_IMAGES = YES;
|
||||
EXECUTABLE_PREFIX = "";
|
||||
GCC_PRECOMPILE_PREFIX_HEADER = YES;
|
||||
GCC_PREFIX_HEADER = "";
|
||||
|
@ -1129,7 +1129,7 @@
|
|||
isa = XCBuildConfiguration;
|
||||
buildSettings = {
|
||||
ALWAYS_SEARCH_USER_PATHS = YES;
|
||||
ARCHS = "$(ARCHS_STANDARD_64_BIT)";
|
||||
COMBINE_HIDPI_IMAGES = YES;
|
||||
EXECUTABLE_PREFIX = "";
|
||||
GCC_GENERATE_DEBUGGING_SYMBOLS = NO;
|
||||
GCC_PRECOMPILE_PREFIX_HEADER = YES;
|
||||
|
|
|
@ -814,8 +814,9 @@ y+=ytranslate; \
|
|||
for(auto it=_children.cbegin()+i; it != _children.cend(); ++it)
|
||||
(*it)->visit(renderer, _modelViewTransform, flags);
|
||||
|
||||
// reset for next frame
|
||||
_orderOfArrival = 0;
|
||||
// FIX ME: Why need to set _orderOfArrival to 0??
|
||||
// Please refer to https://github.com/cocos2d/cocos2d-x/pull/6920
|
||||
// setOrderOfArrival(0);
|
||||
|
||||
director->popMatrix(MATRIX_STACK_TYPE::MATRIX_STACK_MODELVIEW);
|
||||
|
||||
|
|
|
@ -343,6 +343,19 @@ void ScrollView::setContainer(Node * pContainer)
|
|||
this->setViewSize(this->_viewSize);
|
||||
}
|
||||
|
||||
bool ScrollView::hasVisibleParents() const
|
||||
{
|
||||
auto parent = this->getParent();
|
||||
for( auto c = parent; c != nullptr; c = c->getParent() )
|
||||
{
|
||||
if( !c->isVisible() )
|
||||
{
|
||||
return false;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
void ScrollView::relocateContainer(bool animated)
|
||||
{
|
||||
Vec2 oldPoint, min, max;
|
||||
|
@ -625,7 +638,7 @@ void ScrollView::visit(Renderer *renderer, const Mat4 &parentTransform, uint32_t
|
|||
|
||||
bool ScrollView::onTouchBegan(Touch* touch, Event* event)
|
||||
{
|
||||
if (!this->isVisible())
|
||||
if (!this->isVisible() || !this->hasVisibleParents())
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
|
|
@ -256,6 +256,8 @@ public:
|
|||
* CCActionTweenDelegate
|
||||
*/
|
||||
void updateTweenAction(float value, const std::string& key);
|
||||
|
||||
bool hasVisibleParents() const;
|
||||
protected:
|
||||
/**
|
||||
* Relocates the container at the proper offset, in bounds of max/min offsets.
|
||||
|
|
|
@ -664,6 +664,7 @@
|
|||
"cocos/math/MathUtil.h",
|
||||
"cocos/math/MathUtil.inl",
|
||||
"cocos/math/MathUtilNeon.inl",
|
||||
"cocos/math/MathUtilSSE.inl",
|
||||
"cocos/math/Quaternion.cpp",
|
||||
"cocos/math/Quaternion.h",
|
||||
"cocos/math/Quaternion.inl",
|
||||
|
|
|
@ -39,6 +39,7 @@ Classes/ChipmunkTest/ChipmunkTest.cpp \
|
|||
Classes/ClickAndMoveTest/ClickAndMoveTest.cpp \
|
||||
Classes/ClippingNodeTest/ClippingNodeTest.cpp \
|
||||
Classes/CocosDenshionTest/CocosDenshionTest.cpp \
|
||||
Classes/NewAudioEngineTest/NewAudioEngineTest.cpp \
|
||||
Classes/ConfigurationTest/ConfigurationTest.cpp \
|
||||
Classes/ConsoleTest/ConsoleTest.cpp \
|
||||
Classes/CurlTest/CurlTest.cpp \
|
||||
|
|
|
@ -0,0 +1,715 @@
|
|||
/****************************************************************************
|
||||
Copyright (c) 2014 Chukong Technologies Inc.
|
||||
|
||||
http://www.cocos2d-x.org
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in
|
||||
all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
THE SOFTWARE.
|
||||
****************************************************************************/
|
||||
#if CC_TARGET_PLATFORM == CC_PLATFORM_ANDROID || CC_TARGET_PLATFORM == CC_PLATFORM_IOS
|
||||
#include "NewAudioEngineTest.h"
|
||||
#include "ui/CocosGUI.h"
|
||||
|
||||
using namespace cocos2d::ui;
|
||||
|
||||
namespace {
|
||||
|
||||
std::function<Layer*()> createFunctions[] =
|
||||
{
|
||||
CL(AudioControlTest),
|
||||
CL(PlaySimultaneouslyTest),
|
||||
CL(AudioProfileTest),
|
||||
CL(InvalidAudioFileTest),
|
||||
CL(LargeAudioFileTest)
|
||||
};
|
||||
|
||||
unsigned int TEST_CASE_COUNT = sizeof(createFunctions) / sizeof(createFunctions[0]);
|
||||
|
||||
int s_sceneIdx = -1;
|
||||
Layer* createTest(int index)
|
||||
{
|
||||
auto layer = (createFunctions[index])();;
|
||||
return layer;
|
||||
}
|
||||
|
||||
Layer* nextAction()
|
||||
{
|
||||
s_sceneIdx++;
|
||||
s_sceneIdx = s_sceneIdx % TEST_CASE_COUNT;
|
||||
|
||||
return createTest(s_sceneIdx);
|
||||
}
|
||||
|
||||
Layer* backAction()
|
||||
{
|
||||
s_sceneIdx--;
|
||||
if( s_sceneIdx < 0 )
|
||||
s_sceneIdx = TEST_CASE_COUNT -1;
|
||||
|
||||
return createTest(s_sceneIdx);
|
||||
}
|
||||
|
||||
Layer* restartAction()
|
||||
{
|
||||
return createTest(s_sceneIdx);
|
||||
}
|
||||
|
||||
class TextButton : public cocos2d::Label
|
||||
{
|
||||
public:
|
||||
|
||||
static TextButton *create(const std::string& text, const std::function<void(TextButton*)> &onTriggered)
|
||||
{
|
||||
auto ret = new (std::nothrow) TextButton();
|
||||
|
||||
TTFConfig ttfconfig("fonts/arial.ttf",25);
|
||||
if (ret && ret->setTTFConfig(ttfconfig)) {
|
||||
ret->setString(text);
|
||||
ret->_onTriggered = onTriggered;
|
||||
|
||||
ret->autorelease();
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
delete ret;
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
void setEnabled(bool enabled)
|
||||
{
|
||||
_enabled = enabled;
|
||||
if(_enabled){
|
||||
this->setColor(Color3B::WHITE);
|
||||
}
|
||||
else {
|
||||
this->setColor(Color3B::GRAY);
|
||||
}
|
||||
}
|
||||
|
||||
private:
|
||||
TextButton()
|
||||
: _enabled(true)
|
||||
, _onTriggered(nullptr)
|
||||
{
|
||||
auto listener = EventListenerTouchOneByOne::create();
|
||||
listener->setSwallowTouches(true);
|
||||
|
||||
listener->onTouchBegan = CC_CALLBACK_2(TextButton::onTouchBegan, this);
|
||||
listener->onTouchEnded = CC_CALLBACK_2(TextButton::onTouchEnded, this);
|
||||
listener->onTouchCancelled = CC_CALLBACK_2(TextButton::onTouchCancelled, this);
|
||||
|
||||
_eventDispatcher->addEventListenerWithSceneGraphPriority(listener, this);
|
||||
|
||||
}
|
||||
|
||||
bool touchHits(Touch *touch)
|
||||
{
|
||||
auto hitPos = this->convertToNodeSpace(touch->getLocation());
|
||||
if (hitPos.x >= 0 && hitPos.y >= 0 && hitPos.x <= _contentSize.width && hitPos.y <= _contentSize.height) {
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
bool onTouchBegan(Touch *touch, Event *event)
|
||||
{
|
||||
auto hits = touchHits(touch);
|
||||
if (hits){
|
||||
scaleButtonTo(0.95f);
|
||||
}
|
||||
return hits;
|
||||
}
|
||||
|
||||
void onTouchEnded(Touch *touch, Event *event)
|
||||
{
|
||||
if(_enabled) {
|
||||
auto hits = touchHits(touch);
|
||||
if (hits && _onTriggered){
|
||||
_onTriggered(this);
|
||||
}
|
||||
}
|
||||
|
||||
scaleButtonTo(1);
|
||||
}
|
||||
|
||||
void onTouchCancelled(Touch *touch, Event *event)
|
||||
{
|
||||
scaleButtonTo(1);
|
||||
}
|
||||
|
||||
void scaleButtonTo(float scale)
|
||||
{
|
||||
auto action = ScaleTo::create(0.05f, scale);
|
||||
action->setTag(10000);
|
||||
stopActionByTag(10000);
|
||||
runAction(action);
|
||||
}
|
||||
|
||||
std::function<void(TextButton*)> _onTriggered;
|
||||
|
||||
bool _enabled;
|
||||
};
|
||||
|
||||
class SliderEx : public ui::Slider
|
||||
{
|
||||
public:
|
||||
enum class TouchEvent
|
||||
{
|
||||
DOWN,
|
||||
MOVE,
|
||||
UP,
|
||||
CANCEL
|
||||
};
|
||||
typedef std::function<void(SliderEx*,float,TouchEvent)> ccSliderExCallback;
|
||||
|
||||
static SliderEx* create(){
|
||||
auto ret = new (std::nothrow) SliderEx();
|
||||
if (ret && ret->init())
|
||||
{
|
||||
ret->_callback = nullptr;
|
||||
ret->loadBarTexture("cocosui/sliderTrack.png");
|
||||
ret->loadSlidBallTextures("cocosui/sliderThumb.png", "cocosui/sliderThumb.png", "");
|
||||
ret->loadProgressBarTexture("cocosui/sliderProgress.png");
|
||||
|
||||
ret->autorelease();
|
||||
|
||||
return ret;
|
||||
}
|
||||
CC_SAFE_DELETE(ret);
|
||||
return ret;
|
||||
}
|
||||
|
||||
void setCallBack(const ccSliderExCallback& callback){
|
||||
_callback = callback;
|
||||
}
|
||||
|
||||
void setRatio(float ratio) {
|
||||
if (ratio > 1.0f){
|
||||
ratio = 1.0f;
|
||||
}
|
||||
else if (ratio < 0.0f){
|
||||
ratio = 0.0f;
|
||||
}
|
||||
|
||||
_ratio = ratio;
|
||||
_percent = 100 * _ratio;
|
||||
|
||||
float dis = _barLength * _ratio;
|
||||
_slidBallRenderer->setPosition(Vec2(dis, _contentSize.height / 2.0f));
|
||||
if (_scale9Enabled){
|
||||
_progressBarRenderer->setPreferredSize(Size(dis,_progressBarTextureSize.height));
|
||||
}
|
||||
else
|
||||
{
|
||||
auto spriteRenderer = _progressBarRenderer->getSprite();
|
||||
|
||||
if (nullptr != spriteRenderer) {
|
||||
Rect rect = spriteRenderer->getTextureRect();
|
||||
rect.size.width = _progressBarTextureSize.width * _ratio;
|
||||
spriteRenderer->setTextureRect(rect, spriteRenderer->isTextureRectRotated(), rect.size);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
virtual bool onTouchBegan(Touch *touch, Event *unusedEvent) override{
|
||||
auto ret = Slider::onTouchBegan(touch, unusedEvent);
|
||||
if(ret && _callback){
|
||||
_touchEvent = TouchEvent::DOWN;
|
||||
Vec2 nsp = convertToNodeSpace(_touchBeganPosition);
|
||||
_ratio = nsp.x / _barLength;
|
||||
if(_ratio < 0.0f)
|
||||
_ratio = 0.0f;
|
||||
else if(_ratio > 1.0f)
|
||||
_ratio = 1.0f;
|
||||
_callback(this,_ratio,_touchEvent);
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
virtual void onTouchMoved(Touch *touch, Event *unusedEvent) override{
|
||||
_touchEvent = TouchEvent::MOVE;
|
||||
Slider::onTouchMoved(touch, unusedEvent);
|
||||
Vec2 nsp = convertToNodeSpace(_touchMovePosition);
|
||||
_ratio = nsp.x / _barLength;
|
||||
if(_ratio < 0.0f)
|
||||
_ratio = 0.0f;
|
||||
else if(_ratio > 1.0f)
|
||||
_ratio = 1.0f;
|
||||
if(_callback){
|
||||
_callback(this,_ratio,_touchEvent);
|
||||
}
|
||||
}
|
||||
|
||||
virtual void onTouchEnded(Touch *touch, Event *unusedEvent) override{
|
||||
_touchEvent = TouchEvent::UP;
|
||||
Slider::onTouchEnded(touch, unusedEvent);
|
||||
Vec2 nsp = convertToNodeSpace(_touchEndPosition);
|
||||
_ratio = nsp.x / _barLength;
|
||||
if(_ratio < 0.0f)
|
||||
_ratio = 0.0f;
|
||||
else if(_ratio > 1.0f)
|
||||
_ratio = 1.0f;
|
||||
if(_callback){
|
||||
_callback(this,_ratio,_touchEvent);
|
||||
}
|
||||
}
|
||||
|
||||
virtual void onTouchCancelled(Touch *touch, Event *unusedEvent) override{
|
||||
_touchEvent = TouchEvent::CANCEL;
|
||||
Slider::onTouchCancelled(touch, unusedEvent);
|
||||
|
||||
if(_callback){
|
||||
_callback(this,_ratio,_touchEvent);
|
||||
}
|
||||
}
|
||||
|
||||
private:
|
||||
TouchEvent _touchEvent;
|
||||
float _ratio;
|
||||
ccSliderExCallback _callback;
|
||||
};
|
||||
}
|
||||
|
||||
void AudioEngineTestScene::runThisTest()
|
||||
{
|
||||
CCASSERT(AudioEngine::lazyInit(),"Fail to initialize AudioEngine!");
|
||||
|
||||
s_sceneIdx = -1;
|
||||
auto layer = nextAction();
|
||||
addChild(layer);
|
||||
|
||||
Director::getInstance()->replaceScene(this);
|
||||
}
|
||||
|
||||
void AudioEngineTestDemo::backCallback(Ref* sender)
|
||||
{
|
||||
AudioEngine::stopAll();
|
||||
auto scene = new AudioEngineTestScene();
|
||||
auto layer = backAction();
|
||||
|
||||
scene->addChild(layer);
|
||||
Director::getInstance()->replaceScene(scene);
|
||||
scene->release();
|
||||
}
|
||||
|
||||
void AudioEngineTestDemo::nextCallback(Ref* sender)
|
||||
{
|
||||
AudioEngine::stopAll();
|
||||
auto scene = new AudioEngineTestScene();
|
||||
auto layer = nextAction();
|
||||
|
||||
scene->addChild(layer);
|
||||
Director::getInstance()->replaceScene(scene);
|
||||
scene->release();
|
||||
}
|
||||
|
||||
void AudioEngineTestDemo::restartCallback(Ref* sender)
|
||||
{
|
||||
AudioEngine::stopAll();
|
||||
auto scene = new AudioEngineTestScene();
|
||||
auto layer = restartAction();
|
||||
|
||||
scene->addChild(layer);
|
||||
Director::getInstance()->replaceScene(scene);
|
||||
scene->release();
|
||||
}
|
||||
|
||||
std::string AudioEngineTestDemo::title() const
|
||||
{
|
||||
return "New Audio Engine Test";
|
||||
}
|
||||
|
||||
// AudioControlTest
|
||||
bool AudioControlTest::init()
|
||||
{
|
||||
auto ret = AudioEngineTestDemo::init();
|
||||
_audioID = AudioEngine::INVAILD_AUDIO_ID;
|
||||
_loopEnabled = false;
|
||||
_volume = 1.0f;
|
||||
_duration = AudioEngine::TIME_UNKNOWN;
|
||||
_timeRatio = 0.0f;
|
||||
_updateTimeSlider = true;
|
||||
|
||||
std::string fontFilePath = "fonts/arial.ttf";
|
||||
|
||||
auto& layerSize = this->getContentSize();
|
||||
|
||||
auto playItem = TextButton::create("play", [&](TextButton* button){
|
||||
if (_audioID == AudioEngine::INVAILD_AUDIO_ID) {
|
||||
_audioID = AudioEngine::play2d("background.mp3", _loopEnabled, _volume);
|
||||
|
||||
if(_audioID != AudioEngine::INVAILD_AUDIO_ID) {
|
||||
button->setEnabled(false);
|
||||
AudioEngine::setFinishCallback(_audioID, [&](int id, const std::string& filePath){
|
||||
_audioID = AudioEngine::INVAILD_AUDIO_ID;
|
||||
((TextButton*)_playItem)->setEnabled(true);
|
||||
|
||||
_timeRatio = 0.0f;
|
||||
((SliderEx*)_timeSlider)->setRatio(_timeRatio);
|
||||
});
|
||||
}
|
||||
}
|
||||
});
|
||||
_playItem = playItem;
|
||||
playItem->setPosition(layerSize.width * 0.3f,layerSize.height * 0.7f);
|
||||
addChild(playItem);
|
||||
|
||||
auto stopItem = TextButton::create("stop", [&](TextButton* button){
|
||||
if (_audioID != AudioEngine::INVAILD_AUDIO_ID ) {
|
||||
AudioEngine::stop(_audioID);
|
||||
|
||||
_audioID = AudioEngine::INVAILD_AUDIO_ID;
|
||||
((TextButton*)_playItem)->setEnabled(true);
|
||||
}
|
||||
});
|
||||
stopItem->setPosition(layerSize.width * 0.7f,layerSize.height * 0.7f);
|
||||
addChild(stopItem);
|
||||
|
||||
auto pauseItem = TextButton::create("pause", [&](TextButton* button){
|
||||
if (_audioID != AudioEngine::INVAILD_AUDIO_ID ) {
|
||||
AudioEngine::pause(_audioID);
|
||||
}
|
||||
});
|
||||
pauseItem->setPosition(layerSize.width * 0.3f,layerSize.height * 0.6f);
|
||||
addChild(pauseItem);
|
||||
|
||||
auto resumeItem = TextButton::create("resume", [&](TextButton* button){
|
||||
if (_audioID != AudioEngine::INVAILD_AUDIO_ID ) {
|
||||
AudioEngine::resume(_audioID);
|
||||
}
|
||||
});
|
||||
resumeItem->setPosition(layerSize.width * 0.7f,layerSize.height * 0.6f);
|
||||
addChild(resumeItem);
|
||||
|
||||
auto loopItem = TextButton::create("enable-loop", [&](TextButton* button){
|
||||
_loopEnabled = !_loopEnabled;
|
||||
|
||||
if (_audioID != AudioEngine::INVAILD_AUDIO_ID ) {
|
||||
AudioEngine::setLoop(_audioID, _loopEnabled);
|
||||
}
|
||||
if(_loopEnabled){
|
||||
button->setString("disable-loop");
|
||||
}
|
||||
else {
|
||||
button->setString("enable-loop");
|
||||
}
|
||||
});
|
||||
loopItem->setPosition(layerSize.width * 0.3f,layerSize.height * 0.5f);
|
||||
addChild(loopItem);
|
||||
|
||||
auto uncacheItem = TextButton::create("uncache", [&](TextButton* button){
|
||||
AudioEngine::uncache("background.mp3");
|
||||
|
||||
_audioID = AudioEngine::INVAILD_AUDIO_ID;
|
||||
((TextButton*)_playItem)->setEnabled(true);
|
||||
});
|
||||
uncacheItem->setPosition(layerSize.width * 0.7f,layerSize.height * 0.5f);
|
||||
addChild(uncacheItem);
|
||||
|
||||
auto volumeSlider = SliderEx::create();
|
||||
volumeSlider->setPercent(100);
|
||||
volumeSlider->setCallBack([&](SliderEx* sender,float ratio,SliderEx::TouchEvent event){
|
||||
_volume = ratio;
|
||||
log("_volume:%f,event:%d",_volume,event);
|
||||
if (_audioID != AudioEngine::INVAILD_AUDIO_ID ) {
|
||||
AudioEngine::setVolume(_audioID, _volume);
|
||||
}
|
||||
});
|
||||
volumeSlider->setPosition(Vec2(layerSize.width * 0.5f,layerSize.height * 0.35f));
|
||||
addChild(volumeSlider);
|
||||
|
||||
auto timeSlider = SliderEx::create();
|
||||
timeSlider->setCallBack([&](SliderEx* sender,float ratio,SliderEx::TouchEvent event){
|
||||
switch(event){
|
||||
case SliderEx::TouchEvent::MOVE:
|
||||
case SliderEx::TouchEvent::DOWN:
|
||||
_updateTimeSlider = false;
|
||||
break;
|
||||
case SliderEx::TouchEvent::UP:
|
||||
if (_audioID != AudioEngine::INVAILD_AUDIO_ID && _duration != AudioEngine::TIME_UNKNOWN) {
|
||||
AudioEngine::setCurrentTime(_audioID,_duration * ratio);
|
||||
}
|
||||
case SliderEx::TouchEvent::CANCEL:
|
||||
_updateTimeSlider = true;
|
||||
break;
|
||||
}
|
||||
});
|
||||
timeSlider->setPosition(Vec2(layerSize.width * 0.5f,layerSize.height * 0.25f));
|
||||
addChild(timeSlider);
|
||||
_timeSlider = timeSlider;
|
||||
|
||||
auto& volumeSliderPos = volumeSlider->getPosition();
|
||||
auto& sliderSize = volumeSlider->getContentSize();
|
||||
auto volumeLabel = Label::createWithTTF("volume: ", fontFilePath, 20);
|
||||
volumeLabel->setAnchorPoint(Vec2::ANCHOR_MIDDLE_RIGHT);
|
||||
volumeLabel->setPosition(volumeSliderPos.x - sliderSize.width / 2, volumeSliderPos.y);
|
||||
addChild(volumeLabel);
|
||||
|
||||
auto& timeSliderPos = timeSlider->getPosition();
|
||||
auto timeLabel = Label::createWithTTF("time: ", fontFilePath, 20);
|
||||
timeLabel->setAnchorPoint(Vec2::ANCHOR_MIDDLE_RIGHT);
|
||||
timeLabel->setPosition(timeSliderPos.x - sliderSize.width / 2, timeSliderPos.y);
|
||||
addChild(timeLabel);
|
||||
|
||||
this->schedule(schedule_selector(AudioControlTest::update), 0.1f);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
void AudioControlTest::update(float dt)
|
||||
{
|
||||
if (_audioID != AudioEngine::INVAILD_AUDIO_ID ) {
|
||||
if(_duration == AudioEngine::TIME_UNKNOWN){
|
||||
_duration = AudioEngine::getDuration(_audioID);
|
||||
}
|
||||
if(_duration != AudioEngine::TIME_UNKNOWN){
|
||||
auto time = AudioEngine::getCurrentTime(_audioID);
|
||||
_timeRatio = time / _duration;
|
||||
if(_updateTimeSlider){
|
||||
((SliderEx*)_timeSlider)->setRatio(_timeRatio);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
AudioControlTest::~AudioControlTest()
|
||||
{
|
||||
}
|
||||
|
||||
std::string AudioControlTest::title() const
|
||||
{
|
||||
return "audio control test";
|
||||
}
|
||||
|
||||
// PlaySimultaneouslyTest
|
||||
bool PlaySimultaneouslyTest::init()
|
||||
{
|
||||
auto ret = AudioEngineTestDemo::init();
|
||||
|
||||
char text[36];
|
||||
int tmp = 81;
|
||||
for(int index = 0; index < TEST_COUNT; ++index){
|
||||
sprintf(text,"audio/SoundEffectsFX009/FX0%d.mp3",tmp + index);
|
||||
_files[index] = text;
|
||||
}
|
||||
_playingcount = 0;
|
||||
|
||||
auto playItem = TextButton::create("play-simultaneously", [&](TextButton* button){
|
||||
int audioId;
|
||||
_playingcount = 0;
|
||||
button->setEnabled(false);
|
||||
auto startTime = utils::gettime();
|
||||
for(int index = 0; index < TEST_COUNT; ++index){
|
||||
audioId = AudioEngine::play2d(_files[index]);
|
||||
if(audioId != AudioEngine::INVAILD_AUDIO_ID){
|
||||
_playingcount += 1;
|
||||
|
||||
AudioEngine::setFinishCallback(audioId, [&](int id, const std::string& filePath){
|
||||
_playingcount -= 1;
|
||||
if(_playingcount <= 0){
|
||||
((TextButton*)_playItem)->setEnabled(true);
|
||||
}
|
||||
});
|
||||
}
|
||||
else {
|
||||
log("%s,%d,Fail to play file:%s",__FILE__,__LINE__ ,_files[index].c_str());
|
||||
}
|
||||
}
|
||||
log("diff time:%lf",utils::gettime() - startTime);
|
||||
});
|
||||
playItem->setNormalizedPosition(Vec2(0.5f,0.5f));
|
||||
this->addChild(playItem);
|
||||
_playItem = playItem;
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
PlaySimultaneouslyTest::~PlaySimultaneouslyTest()
|
||||
{
|
||||
}
|
||||
|
||||
std::string PlaySimultaneouslyTest::title() const
|
||||
{
|
||||
return "Simultaneously play multiple audio";
|
||||
}
|
||||
|
||||
// AudioProfileTest
|
||||
bool AudioProfileTest::init()
|
||||
{
|
||||
auto ret = AudioEngineTestDemo::init();
|
||||
|
||||
char text[30];
|
||||
_files[0] = "background.mp3";
|
||||
#if CC_TARGET_PLATFORM == CC_PLATFORM_IOS
|
||||
_files[1] = "background.caf";
|
||||
#else
|
||||
_files[1] = "background.ogg";
|
||||
#endif
|
||||
_files[2] = "background.wav";
|
||||
_files[3] = "pew-pew-lei.wav";
|
||||
|
||||
std::string fontFilePath = "fonts/arial.ttf";
|
||||
_minDelay = 1.0f;
|
||||
_time = 0.0f;
|
||||
|
||||
_audioProfile.name = "AudioProfileTest";
|
||||
_audioProfile.maxInstances = 3;
|
||||
_audioProfile.minDelay = 1.0;
|
||||
|
||||
Vec2 pos(0.5f,0.7f);
|
||||
|
||||
for(int index = 0; index < FILE_COUNT; ++index){
|
||||
sprintf(text,"play %s",_files[index].c_str());
|
||||
|
||||
auto playItem = TextButton::create(text, [&](TextButton* button){
|
||||
int index = button->getTag();
|
||||
auto id = AudioEngine::play2d(_files[index], false, 1.0f, &_audioProfile);
|
||||
if(id != AudioEngine::INVAILD_AUDIO_ID){
|
||||
_time = _minDelay;
|
||||
_audioCount += 1;
|
||||
char show[30];
|
||||
sprintf(show,"audio count:%d",_audioCount);
|
||||
_showLabel->setString(show);
|
||||
|
||||
AudioEngine::setFinishCallback(id, [&](int id, const std::string& filePath){
|
||||
_audioCount -= 1;
|
||||
char show[30];
|
||||
sprintf(show,"audio count:%d",_audioCount);
|
||||
_showLabel->setString(show);
|
||||
});
|
||||
}
|
||||
|
||||
});
|
||||
playItem->setTag(index);
|
||||
playItem->setNormalizedPosition(pos);
|
||||
this->addChild(playItem);
|
||||
pos.y -= 0.1f;
|
||||
|
||||
}
|
||||
|
||||
Vec2 origin = Director::getInstance()->getVisibleOrigin();
|
||||
Size size = Director::getInstance()->getVisibleSize();
|
||||
|
||||
auto profileInfoLabel = Label::createWithTTF("AudioProfile Info:\n max instance:3 \n minimum delay:1.0", fontFilePath, 12);
|
||||
profileInfoLabel->setAnchorPoint(Vec2::ANCHOR_MIDDLE_LEFT);
|
||||
profileInfoLabel->setPosition(Vec2(origin.x, origin.y + size.height * 0.65f));
|
||||
addChild(profileInfoLabel);
|
||||
|
||||
_audioCount = 0;
|
||||
_showLabel = Label::createWithTTF("audio count:0", fontFilePath, 12);
|
||||
_showLabel->setAnchorPoint(Vec2::ANCHOR_MIDDLE_LEFT);
|
||||
_showLabel->setPosition(Vec2(origin.x, origin.y + size.height * 0.5f));
|
||||
addChild(_showLabel);
|
||||
|
||||
auto timeSlider = SliderEx::create();
|
||||
timeSlider->setEnabled(false);
|
||||
timeSlider->setNormalizedPosition(pos);
|
||||
addChild(timeSlider);
|
||||
_timeSlider = timeSlider;
|
||||
|
||||
this->schedule(schedule_selector(AudioControlTest::update), 0.05f);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
void AudioProfileTest::update(float dt)
|
||||
{
|
||||
if(_time > 0.0f)
|
||||
{
|
||||
_time -= dt;
|
||||
((SliderEx*)_timeSlider)->setRatio(_time / _minDelay);
|
||||
}
|
||||
}
|
||||
|
||||
AudioProfileTest::~AudioProfileTest()
|
||||
{
|
||||
}
|
||||
|
||||
std::string AudioProfileTest::title() const
|
||||
{
|
||||
return "AudioProfileTest";
|
||||
}
|
||||
|
||||
std::string AudioProfileTest::subtitle() const
|
||||
{
|
||||
return "See the console.";
|
||||
}
|
||||
|
||||
// InvalidAudioFileTest
|
||||
bool InvalidAudioFileTest::init()
|
||||
{
|
||||
auto ret = AudioEngineTestDemo::init();
|
||||
|
||||
auto playItem = TextButton::create("play unsupported media type", [&](TextButton* button){
|
||||
#if CC_TARGET_PLATFORM == CC_PLATFORM_IOS
|
||||
AudioEngine::play2d("background.ogg");
|
||||
#elif CC_TARGET_PLATFORM == CC_PLATFORM_ANDROID
|
||||
AudioEngine::play2d("background.caf");
|
||||
#endif
|
||||
});
|
||||
playItem->setNormalizedPosition(Vec2(0.5f, 0.6f));
|
||||
this->addChild(playItem);
|
||||
|
||||
auto playItem2 = TextButton::create("play not-existent file", [&](TextButton* button){
|
||||
AudioEngine::play2d("not-existent file.mp3");
|
||||
});
|
||||
playItem2->setNormalizedPosition(Vec2(0.5f, 0.4f));
|
||||
this->addChild(playItem2);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
InvalidAudioFileTest::~InvalidAudioFileTest()
|
||||
{
|
||||
}
|
||||
|
||||
std::string InvalidAudioFileTest::title() const
|
||||
{
|
||||
return "Test invalid audio file";
|
||||
}
|
||||
|
||||
std::string InvalidAudioFileTest::subtitle() const
|
||||
{
|
||||
return "Not crash,please see the console.";
|
||||
}
|
||||
|
||||
// LargeAudioFileTest
|
||||
bool LargeAudioFileTest::init()
|
||||
{
|
||||
auto ret = AudioEngineTestDemo::init();
|
||||
|
||||
auto playItem = TextButton::create("play large audio file", [&](TextButton* button){
|
||||
AudioEngine::play2d("audio/Chee Lai(Arise).mp3");
|
||||
});
|
||||
playItem->setNormalizedPosition(Vec2::ANCHOR_MIDDLE);
|
||||
this->addChild(playItem);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
LargeAudioFileTest::~LargeAudioFileTest()
|
||||
{
|
||||
}
|
||||
|
||||
std::string LargeAudioFileTest::title() const
|
||||
{
|
||||
return "Test large audio file";
|
||||
}
|
||||
|
||||
#endif
|
|
@ -0,0 +1,153 @@
|
|||
/****************************************************************************
|
||||
Copyright (c) 2014 Chukong Technologies Inc.
|
||||
|
||||
http://www.cocos2d-x.org
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in
|
||||
all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
THE SOFTWARE.
|
||||
****************************************************************************/
|
||||
#if CC_TARGET_PLATFORM == CC_PLATFORM_ANDROID || CC_TARGET_PLATFORM == CC_PLATFORM_IOS
|
||||
#ifndef __NEWAUDIOENGINE_TEST_H_
|
||||
#define __NEWAUDIOENGINE_TEST_H_
|
||||
|
||||
#include "cocos2d.h"
|
||||
#include "../testBasic.h"
|
||||
#include "../BaseTest.h"
|
||||
|
||||
#include "audio/include/AudioEngine.h"
|
||||
|
||||
using namespace cocos2d;
|
||||
|
||||
class AudioEngineTestScene : public TestScene
|
||||
{
|
||||
public:
|
||||
virtual void runThisTest();
|
||||
};
|
||||
|
||||
class AudioEngineTestDemo : public BaseTest
|
||||
{
|
||||
public:
|
||||
virtual std::string title() const override;
|
||||
void backCallback(Ref* sender);
|
||||
void nextCallback(Ref* sender);
|
||||
void restartCallback(Ref* sender);
|
||||
|
||||
};
|
||||
|
||||
class AudioControlTest : public AudioEngineTestDemo
|
||||
{
|
||||
public:
|
||||
CREATE_FUNC(AudioControlTest);
|
||||
|
||||
virtual ~AudioControlTest();
|
||||
|
||||
virtual bool init();
|
||||
|
||||
virtual void update(float dt);
|
||||
|
||||
virtual std::string title() const override;
|
||||
|
||||
private:
|
||||
int _audioID;
|
||||
bool _loopEnabled;
|
||||
float _volume;
|
||||
float _duration;
|
||||
float _timeRatio;
|
||||
|
||||
void* _playItem;
|
||||
void* _timeSlider;
|
||||
bool _updateTimeSlider;
|
||||
};
|
||||
|
||||
class PlaySimultaneouslyTest : public AudioEngineTestDemo
|
||||
{
|
||||
public:
|
||||
CREATE_FUNC(PlaySimultaneouslyTest);
|
||||
|
||||
virtual ~PlaySimultaneouslyTest();
|
||||
|
||||
virtual bool init();
|
||||
|
||||
virtual std::string title() const override;
|
||||
private:
|
||||
static const int TEST_COUNT = 10;
|
||||
std::string _files[TEST_COUNT];
|
||||
|
||||
void* _playItem;
|
||||
int _playingcount;
|
||||
};
|
||||
|
||||
class AudioProfileTest : public AudioEngineTestDemo
|
||||
{
|
||||
public:
|
||||
CREATE_FUNC(AudioProfileTest);
|
||||
|
||||
virtual ~AudioProfileTest();
|
||||
|
||||
virtual bool init();
|
||||
|
||||
virtual std::string title() const override;
|
||||
virtual std::string subtitle() const override;
|
||||
|
||||
virtual void update(float dt);
|
||||
|
||||
private:
|
||||
static const int FILE_COUNT = 4;
|
||||
std::string _files[FILE_COUNT];
|
||||
AudioProfile _audioProfile;
|
||||
|
||||
int _audioCount;
|
||||
Label* _showLabel;
|
||||
float _time;
|
||||
float _minDelay;
|
||||
void* _timeSlider;
|
||||
};
|
||||
|
||||
class InvalidAudioFileTest : public AudioEngineTestDemo
|
||||
{
|
||||
public:
|
||||
CREATE_FUNC(InvalidAudioFileTest);
|
||||
|
||||
virtual ~InvalidAudioFileTest();
|
||||
|
||||
virtual bool init();
|
||||
|
||||
virtual std::string title() const override;
|
||||
virtual std::string subtitle() const override;
|
||||
|
||||
private:
|
||||
|
||||
};
|
||||
|
||||
class LargeAudioFileTest : public AudioEngineTestDemo
|
||||
{
|
||||
public:
|
||||
CREATE_FUNC(LargeAudioFileTest);
|
||||
|
||||
virtual ~LargeAudioFileTest();
|
||||
|
||||
virtual bool init();
|
||||
|
||||
virtual std::string title() const override;
|
||||
|
||||
private:
|
||||
|
||||
};
|
||||
|
||||
#endif /* defined(__NEWAUDIOENGINE_TEST_H_) */
|
||||
#endif
|
|
@ -39,6 +39,9 @@ Controller g_aTestNames[] = {
|
|||
{ "Actions - Ease", [](){return new ActionsEaseTestScene();} },
|
||||
{ "Actions - Progress", [](){return new ProgressActionsTestScene(); } },
|
||||
{ "Audio - CocosDenshion", []() { return new CocosDenshionTestScene(); } },
|
||||
#if (CC_TARGET_PLATFORM == CC_PLATFORM_ANDROID || CC_TARGET_PLATFORM == CC_PLATFORM_IOS)
|
||||
{ "Audio - NewAudioEngine", []() { return new AudioEngineTestScene(); } },
|
||||
#endif
|
||||
{ "Box2d - Basic", []() { return new Box2DTestScene(); } },
|
||||
{ "Box2d - TestBed", []() { return new Box2dTestBedScene(); } },
|
||||
{ "Bugs", []() { return new BugsTestScene(); } },
|
||||
|
|
|
@ -37,6 +37,9 @@
|
|||
#include "PerformanceTest/PerformanceTest.h"
|
||||
#include "ZwoptexTest/ZwoptexTest.h"
|
||||
#include "CocosDenshionTest/CocosDenshionTest.h"
|
||||
#if (CC_TARGET_PLATFORM == CC_PLATFORM_ANDROID || CC_TARGET_PLATFORM == CC_PLATFORM_IOS)
|
||||
#include "NewAudioEngineTest/NewAudioEngineTest.h"
|
||||
#endif
|
||||
#if (CC_TARGET_PLATFORM != CC_PLATFORM_EMSCRIPEN)
|
||||
#if (CC_TARGET_PLATFORM != CC_PLATFORM_MARMALADE)
|
||||
// bada don't support libcurl
|
||||
|
|
|
@ -1 +1 @@
|
|||
Subproject commit c1db553615789a1545d495d0d0fd6f620547f99d
|
||||
Subproject commit a8496d540c174236bec0d5a33457340571699f19
|
|
@ -11,7 +11,7 @@ android_headers = -I%(androidndkdir)s/platforms/android-14/arch-arm/usr/include
|
|||
android_flags = -D_SIZE_T_DEFINED_
|
||||
|
||||
clang_headers = -I%(clangllvmdir)s/lib/clang/3.3/include
|
||||
clang_flags = -nostdinc -x c++ -std=c++11
|
||||
clang_flags = -nostdinc -x c++ -std=c++11 -U __SSE__
|
||||
|
||||
cocos_headers = -I%(cocosdir)s/cocos -I%(cocosdir)s/cocos/platform/android
|
||||
cocos_flags = -DANDROID
|
||||
|
|
|
@ -11,7 +11,7 @@ android_headers = -I%(androidndkdir)s/platforms/android-14/arch-arm/usr/include
|
|||
android_flags = -D_SIZE_T_DEFINED_
|
||||
|
||||
clang_headers = -I%(clangllvmdir)s/lib/clang/3.3/include
|
||||
clang_flags = -nostdinc -x c++ -std=c++11
|
||||
clang_flags = -nostdinc -x c++ -std=c++11 -U __SSE__
|
||||
|
||||
cocos_headers = -I%(cocosdir)s/cocos -I%(cocosdir)s/cocos/platform/android
|
||||
cocos_flags = -DANDROID
|
||||
|
|
|
@ -11,7 +11,7 @@ android_headers = -I%(androidndkdir)s/platforms/android-14/arch-arm/usr/include
|
|||
android_flags = -D_SIZE_T_DEFINED_
|
||||
|
||||
clang_headers = -I%(clangllvmdir)s/lib/clang/3.3/include
|
||||
clang_flags = -nostdinc -x c++ -std=c++11
|
||||
clang_flags = -nostdinc -x c++ -std=c++11 -U __SSE__
|
||||
|
||||
cocos_headers = -I%(cocosdir)s -I%(cocosdir)s/cocos -I%(cocosdir)s/cocos/editor-support -I%(cocosdir)s/cocos/platform/android
|
||||
|
||||
|
|
|
@ -11,7 +11,7 @@ android_headers = -I%(androidndkdir)s/platforms/android-14/arch-arm/usr/include
|
|||
android_flags = -D_SIZE_T_DEFINED_
|
||||
|
||||
clang_headers = -I%(clangllvmdir)s/lib/clang/3.3/include
|
||||
clang_flags = -nostdinc -x c++ -std=c++11
|
||||
clang_flags = -nostdinc -x c++ -std=c++11 -U __SSE__
|
||||
|
||||
cocos_headers = -I%(cocosdir)s -I%(cocosdir)s/cocos -I%(cocosdir)s/cocos/platform/android
|
||||
|
||||
|
|
|
@ -13,7 +13,7 @@ android_headers = -I%(androidndkdir)s/platforms/android-14/arch-arm/usr/include
|
|||
android_flags = -D_SIZE_T_DEFINED_
|
||||
|
||||
clang_headers = -I%(clangllvmdir)s/lib/clang/3.3/include
|
||||
clang_flags = -nostdinc -x c++ -std=c++11
|
||||
clang_flags = -nostdinc -x c++ -std=c++11 -U __SSE__
|
||||
|
||||
cocos_headers = -I%(cocosdir)s/cocos -I%(cocosdir)s/cocos/base -I%(cocosdir)s/cocos/platform/android
|
||||
cocos_flags = -DANDROID
|
||||
|
|
|
@ -11,7 +11,7 @@ android_headers = -I%(androidndkdir)s/platforms/android-14/arch-arm/usr/include
|
|||
android_flags = -D_SIZE_T_DEFINED_
|
||||
|
||||
clang_headers = -I%(clangllvmdir)s/lib/clang/3.3/include
|
||||
clang_flags = -nostdinc -x c++ -std=c++11
|
||||
clang_flags = -nostdinc -x c++ -std=c++11 -U __SSE__
|
||||
|
||||
cocos_headers = -I%(cocosdir)s/cocos -I%(cocosdir)s/cocos/editor-support -I%(cocosdir)s/cocos/platform/android
|
||||
|
||||
|
|
|
@ -13,7 +13,7 @@ android_headers = -I%(androidndkdir)s/platforms/android-14/arch-arm/usr/include
|
|||
android_flags = -D_SIZE_T_DEFINED_
|
||||
|
||||
clang_headers = -I%(clangllvmdir)s/lib/clang/3.3/include
|
||||
clang_flags = -nostdinc -x c++ -std=c++11
|
||||
clang_flags = -nostdinc -x c++ -std=c++11 -U __SSE__
|
||||
|
||||
cocos_headers = -I%(cocosdir)s/cocos -I%(cocosdir)s/cocos/editor-support -I%(cocosdir)s/cocos/platform/android
|
||||
|
||||
|
|
|
@ -11,7 +11,7 @@ android_headers = -I%(androidndkdir)s/platforms/android-14/arch-arm/usr/include
|
|||
android_flags = -D_SIZE_T_DEFINED_
|
||||
|
||||
clang_headers = -I%(clangllvmdir)s/lib/clang/3.3/include
|
||||
clang_flags = -nostdinc -x c++ -std=c++11
|
||||
clang_flags = -nostdinc -x c++ -std=c++11 -U __SSE__
|
||||
|
||||
cocos_headers = -I%(cocosdir)s -I%(cocosdir)s/cocos/editor-support -I%(cocosdir)s/cocos -I%(cocosdir)s/cocos/platform/android
|
||||
|
||||
|
|
|
@ -13,7 +13,7 @@ android_headers = -I%(androidndkdir)s/platforms/android-14/arch-arm/usr/include
|
|||
android_flags = -D_SIZE_T_DEFINED_
|
||||
|
||||
clang_headers = -I%(clangllvmdir)s/lib/clang/3.3/include
|
||||
clang_flags = -nostdinc -x c++ -std=c++11
|
||||
clang_flags = -nostdinc -x c++ -std=c++11 -U __SSE__
|
||||
|
||||
cocos_headers = -I%(cocosdir)s/cocos -I%(cocosdir)s/cocos/platform/android
|
||||
|
||||
|
|
|
@ -11,7 +11,7 @@ android_headers = -I%(androidndkdir)s/platforms/android-14/arch-arm/usr/include
|
|||
android_flags = -D_SIZE_T_DEFINED_
|
||||
|
||||
clang_headers = -I%(clangllvmdir)s/lib/clang/3.3/include
|
||||
clang_flags = -nostdinc -x c++ -std=c++11
|
||||
clang_flags = -nostdinc -x c++ -std=c++11 -U __SSE__
|
||||
|
||||
cocos_headers = -I%(cocosdir)s/cocos -I%(cocosdir)s/cocos/editor-support -I%(cocosdir)s/cocos/platform/android
|
||||
|
||||
|
|
|
@ -14,7 +14,7 @@ android_headers = -I%(androidndkdir)s/platforms/android-14/arch-arm/usr/include
|
|||
android_flags = -D_SIZE_T_DEFINED_
|
||||
|
||||
clang_headers = -I%(clangllvmdir)s/lib/clang/3.3/include
|
||||
clang_flags = -nostdinc -x c++ -std=c++11
|
||||
clang_flags = -nostdinc -x c++ -std=c++11 -U __SSE__
|
||||
|
||||
cocos_headers = -I%(cocosdir)s/external -I%(cocosdir)s/cocos -I%(cocosdir)s/cocos/editor-support -I%(cocosdir)s/cocos/platform/android
|
||||
|
||||
|
|
|
@ -14,7 +14,7 @@ android_headers = -I%(androidndkdir)s/platforms/android-14/arch-arm/usr/include
|
|||
android_flags = -D_SIZE_T_DEFINED_
|
||||
|
||||
clang_headers = -I%(clangllvmdir)s/lib/clang/3.3/include
|
||||
clang_flags = -nostdinc -x c++ -std=c++11
|
||||
clang_flags = -nostdinc -x c++ -std=c++11 -U __SSE__
|
||||
|
||||
cocos_headers = -I%(cocosdir)s/cocos -I%(cocosdir)s/cocos/editor-support -I%(cocosdir)s/cocos/platform/android
|
||||
|
||||
|
|
Loading…
Reference in New Issue