1import MusicQueue from '@/core/musicQueue'; 2import MusicSheet from '@/core/musicSheet'; 3import {check, PERMISSIONS, request} from 'react-native-permissions'; 4import TrackPlayer, {Capability} from 'react-native-track-player'; 5import 'react-native-get-random-values'; 6import Config from '@/core/config'; 7import RNBootSplash from 'react-native-bootsplash'; 8import Download from '@/core/download'; 9import pathConst from '@/constants/pathConst'; 10import {checkAndCreateDir} from '@/utils/fileUtils'; 11import {errorLog, trace} from '@/utils/log'; 12import MediaMeta from '@/core/mediaMeta'; 13import Cache from '@/core/cache'; 14import PluginManager from '@/core/pluginManager'; 15import Network from '@/core/network'; 16 17/** app加载前执行 18 * 1. 检查权限 19 * 2. 数据初始化 20 * 3. 21 */ 22async function _bootstrap() { 23 // 1. 检查权限 24 const [readStoragePermission, writeStoragePermission] = await Promise.all([ 25 check(PERMISSIONS.ANDROID.READ_EXTERNAL_STORAGE), 26 check(PERMISSIONS.ANDROID.WRITE_EXTERNAL_STORAGE), 27 ]); 28 if ( 29 !( 30 readStoragePermission === 'granted' && 31 writeStoragePermission === 'granted' 32 ) 33 ) { 34 await request(PERMISSIONS.ANDROID.READ_EXTERNAL_STORAGE); 35 await request(PERMISSIONS.ANDROID.WRITE_EXTERNAL_STORAGE); 36 } 37 38 // 2. 数据初始化 39 /** 初始化路径 */ 40 await setupFolder(); 41 trace('文件夹初始化完成'); 42 // 加载配置 43 await Promise.all([ 44 Config.setup(), 45 MediaMeta.setup(), 46 MusicSheet.setup(), 47 Network.setup(), 48 ]); 49 trace('配置初始化完成'); 50 // 加载插件 51 try { 52 await TrackPlayer.setupPlayer({ 53 maxCacheSize: 54 Config.get('setting.basic.maxCacheSize') ?? 1024 * 1024 * 512, 55 }); 56 } catch (e: any) { 57 if ( 58 e?.message !== 59 'The player has already been initialized via setupPlayer.' 60 ) { 61 throw e; 62 } 63 } 64 await TrackPlayer.updateOptions({ 65 progressUpdateEventInterval: 1, 66 alwaysPauseOnInterruption: true, 67 capabilities: [ 68 Capability.Play, 69 Capability.Pause, 70 Capability.SkipToNext, 71 Capability.SkipToPrevious, 72 ], 73 compactCapabilities: [ 74 Capability.Play, 75 Capability.Pause, 76 Capability.SkipToNext, 77 Capability.SkipToPrevious, 78 ], 79 notificationCapabilities: [ 80 Capability.Play, 81 Capability.Pause, 82 Capability.SkipToNext, 83 Capability.SkipToPrevious, 84 ], 85 }); 86 trace('播放器初始化完成'); 87 await Cache.setup(); 88 trace('缓存初始化完成'); 89 await Download.setup(); 90 trace('下载初始化完成'); 91 await PluginManager.setup(); 92 trace('插件初始化完成'); 93 await MusicQueue.setup(); 94 trace('播放列表初始化完成'); 95 96 ErrorUtils.setGlobalHandler(error => { 97 errorLog('未捕获的错误', error); 98 }); 99} 100 101/** 初始化 */ 102async function setupFolder() { 103 await Promise.all([ 104 checkAndCreateDir(pathConst.dataPath), 105 checkAndCreateDir(pathConst.logPath), 106 checkAndCreateDir(pathConst.cachePath), 107 checkAndCreateDir(pathConst.storagePath), 108 checkAndCreateDir(pathConst.pluginPath), 109 checkAndCreateDir(pathConst.lrcCachePath), 110 ]); 111} 112 113export default async function () { 114 try { 115 await _bootstrap(); 116 } catch (e) { 117 errorLog('初始化出错', e); 118 console.log(e); 119 } 120 // 隐藏开屏动画 121 console.log('HIDE'); 122 RNBootSplash.hide({fade: true}); 123} 124