我正在尝试与 alan 语音助手 api 一起创建一个音乐应用程序,但它给了我以下错误:
E/flutter (29724): [ERROR:flutter/lib/ui/ui_dart_state.cc(199)] Unhandled Exception:
PlatformException(Unexpected error!, null, java.lang.IllegalStateException
E/flutter (29724): at android.media.MediaPlayer.nativeSetDataSource(Native Method)
E/flutter (29724): at android.media.MediaPlayer.setDataSource(MediaPlayer.java:1205)
E/flutter (29724): at android.media.MediaPlayer.setDataSource(MediaPlayer.java:1192)
E/flutter (29724): at android.media.MediaPlayer.setDataSource(MediaPlayer.java:1157)
E/flutter (29724): at xyz.luan.audioplayers.WrappedMediaPlayer.setUrl(WrappedMediaPlayer.kt:37)
E/flutter (29724): at
xyz.luan.audioplayers.AudioplayersPlugin.handleMethodCall(AudioplayersPlugin.kt:59)
E/flutter (29724): at
xyz.luan.audioplayers.AudioplayersPlugin.onMethodCall(AudioplayersPlugin.kt:34)
E/flutter (29724): at
io.flutter.plugin.common.MethodChannel$IncomingMethodCallHandler.onMessage(MethodChannel.java:233)
E/flutter (29724): at
io.flutter.embedding.engine.dart.DartMessenger.handleMessageFromDart(DartMessenger.java:85)
E/flutter (29724): at
io.flutter.embedding.engine.FlutterJNI.handlePlatformMessage(FlutterJNI.java:818)
E/flutter (29724): at android.os.MessageQueue.nativePollOnce(Native Method)
E/flutter (29724): at android.os.MessageQueue.next(MessageQueue.java:335)
E/flutter (29724): at android.os.Looper.loop(Looper.java:183)
E/flutter (29724): at android.app.ActivityThread.main(ActivityThread.java:8010)
E/flutter (29724): at java.lang.reflect.Method.invoke(Native Method)
E/flutter (29724): at
com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:631)
E/flutter (29724): at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:978)
E/flutter (29724): , null)
E/flutter (29724): #0 StandardMethodCodec.decodeEnvelope
(package:flutter/src/services/message_codecs.dart:597:7)
E/flutter (29724): #1 MethodChannel._invokeMethod
(package:flutter/src/services/platform_channel.dart:158:18)
E/flutter (29724): <asynchronous suspension>
E/flutter (29724): #2 AudioPlayer.play (package:audioplayers/audioplayers.dart:342:24)
E/flutter (29724): <asynchronous suspension>
编码:
import 'package:ai_radio/models/radio.dart';
import 'package:ai_radio/pages/upload.dart';
import 'package:ai_radio/utils/song.dart';
import 'package:audioplayers/audioplayers.dart';
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:flutter/services.dart';
import 'package:velocity_x/velocity_x.dart';
import 'package:ai_radio/utils/ai_util.dart';
import 'package:alan_voice/alan_voice.dart';
import 'package:ai_radio/utils/get_songs.dart';
import 'package:audioplayers/audio_cache.dart';
class HomePage extends StatefulWidget {
@override
_HomePageState createState() => _HomePageState();
}
class _HomePageState extends State<HomePage> {
List<MyRadio> radios;
Song _selectedRadio;
Color _selectedColor;
bool _isPlaying = false;
var allSongs;
final AudioPlayer _audioPlayer = AudioPlayer();
@override
void initState() {
super.initState();
setupAlan();
getSongs();
_audioPlayer.onPlayerStateChanged.listen((event) {
if(event==AudioPlayerState.PLAYING)
_isPlaying = true;
else
_isPlaying = false;
setState(() {});
});
}
void getSongs() async
{
GetSongs songObj = GetSongs();
await songObj.getData();
songObj.sortList();
setState(() {
allSongs = songObj.data;
_selectedRadio = allSongs[0];
_selectedColor = Color(int.tryParse(_selectedRadio.color));
});
}
void upload(){
Navigator.push(context, MaterialPageRoute(builder: (context){
return Upload();
}));
}
setupAlan(){
AlanVoice.addButton(
"81efcd865bde618eb45ed761cece2fee2e956eca572e1d8b807a3e2338fdd0dc/stage",
buttonAlign: AlanVoice.BUTTON_ALIGN_RIGHT);
AlanVoice.callbacks.add((command)=>_handleCommand(command.data));
}
_handleCommand(Map<String,dynamic> response)
{
switch (response['command']){
case 'play':
playMusic(_selectedRadio);
break;
case 'stop':
_audioPlayer.stop();
break;
case 'next':
int index = _selectedRadio.id;
Song newSong;
/*
for(int i=0;i<allSongs.length;i++)
print(allSongs[i].id.toString()+" "+allSongs[i].song_name);
print(_selectedRadio.id);
print("+++++++++++++++");
int index = (_selectedRadio.id+1)%(allSongs.length-1);
print(index);
print("----------");
Song newSong;
newSong = allSongs.firstWhere((obj)=>obj.id==index);
print(newSong.song_name);
print("++++++++++");
allSongs.remove(newSong);
allSongs.insert(0,newSong);
playMusic(newSong.song_url);
break;
*/
if(index+1>allSongs.length-1){
newSong = allSongs.firstWhere((element) => element.id == 0);
allSongs.remove(newSong);
allSongs.insert(0,newSong);
}
else{
newSong = allSongs.firstWhere((element) => element.id == index+1);
allSongs.remove(newSong);
allSongs.insert(0,newSong);
}
playMusic(newSong);
break;
case 'previous':
final index = _selectedRadio.id;
Song newSong;
if(index-1 < 0){
for (int i=0;i<allSongs.length;i++){
if(allSongs[i].id==allSongs.length-1){
newSong = allSongs[i];
allSongs.remove(newSong);
allSongs.insert(0,newSong);
playMusic(_selectedRadio);
break;
}
}
}
else{
for (int i=0;i<allSongs.length;i++){
print(index);
print("+++++++++++++++++++++++");
if(allSongs[i].id==index-1){
print(allSongs[i].id);
newSong = allSongs[i];
allSongs.remove(newSong);
allSongs.insert(0,newSong);
_selectedRadio = newSong;
setState(() {});
break;
}
}
}
break;
case 'upload':
upload();
break;
default:
print("Command was ${response['command']}");
}
}
playMusic(Song song) {
_selectedRadio = song;
print(_selectedRadio.song_name);
setState(() {});
_audioPlayer.play(song.song_url,isLocal: true);
}
void changeColor(int index)
{
print(index);
setState(() {
_selectedRadio = allSongs[index];
_selectedColor = Color(int.tryParse(_selectedRadio.color));
});
}
@override
Widget build(BuildContext context) {
return Scaffold(
drawer: Drawer(),
body: Stack(
fit: StackFit.expand,
children: [
VxAnimatedBox()
.size(context.screenWidth, context.screenHeight)
.withGradient(
LinearGradient(
colors: [
AIColors.primaryColor2,
_selectedColor ?? AIColors.primaryColor1,
],
begin: Alignment.topLeft,
end: Alignment.bottomRight
),
)
.make(),
AppBar(
backgroundColor: Colors.transparent,
elevation: 0.0,
centerTitle: true,
title: "AI Radio".text.xl3.bold.white.make().shimmer(
primaryColor: Vx.purple300, secondaryColor: Colors.white),
).h(100.0).p16(),
allSongs!=null? VxSwiper.builder(
aspectRatio: 1.0,
realPage: 3,
itemCount: allSongs!=null?allSongs.length:0,
onPageChanged: (index){
changeColor(index);
},
itemBuilder: (context, index) {
final rad = allSongs[index];
return VxBox(
child: ZStack([
Positioned(
top:0.0,
right:0.0,
child: VxBox(
child: Padding(
padding: const EdgeInsets.all(12.0),
child: Text(
rad.category,
style: TextStyle(
color: Colors.white,
fontSize: 12
),
),
)
).black.alignCenter.withRounded(value:10.0).make().h(40.0).px8()
),
Align(
alignment: Alignment.bottomCenter,
child: VStack(
[
Text(
rad.song_name,
style: TextStyle(
color: Colors.white,
fontSize: 16,
fontWeight: FontWeight.bold
),
),
5.heightBox,
Text(
rad.artist_name,
style: TextStyle(
color: Colors.white,
fontWeight: FontWeight.w400
),
),
//rad.tagline.text.sm.white.semiBold.make()
],
crossAlignment: CrossAxisAlignment.center,
)
),
Align(
alignment: Alignment.center,
child: VStack(
[
Icon(
CupertinoIcons.play_circle,
color: Colors.white,
),
10.heightBox,
"Double tap to play".text.gray300.make()
],
crossAlignment: CrossAxisAlignment.center,
)
)
],
clip: Clip.antiAlias,
)
).clip(Clip.antiAlias)
.bgImage(
DecorationImage(
image: AssetImage(rad.image_url),
fit: BoxFit.cover,
colorFilter: ColorFilter.mode(
Colors.black.withOpacity(0.3), BlendMode.darken
)
)
)
.withRounded(value: 60.0)
.border(color: Colors.black, width: 2.0)
.make()
.onDoubleTap(() {
_selectedRadio = rad;
playMusic(rad);
})
.p16();
}
).centered():Center(child:CircularProgressIndicator()),
Align(
alignment: Alignment.bottomCenter,
child: VStack(
[
if(_isPlaying)
"Playing Now - ${_selectedRadio.song_name} ".text.white.makeCentered(),
Icon(
_isPlaying?CupertinoIcons.stop_circle_fill:CupertinoIcons.play_circle_fill,
color: Colors.white,
size: 50.0,
).onInkTap(() {
if(_isPlaying){
_audioPlayer.stop();
}
else{
playMusic(_selectedRadio);
}
})
,
],
crossAlignment: CrossAxisAlignment.center,
)
).pOnly(bottom: context.percentHeight*12),
],
),
);
}
}
**有两件事我无法弄清楚:
- 错误,我不知道为什么会发生。
- 当我尝试根据 allSongs id 更改刷卡时,逻辑似乎不起作用,我确信它在逻辑上是正确的,但它会渲染一些其他卡并播放正确的歌曲。**