Flutter 'value >= min && value <= max': is not true - flutter

I am building a simple music player type app. I am facing an issue when my audio completed the time it's showing
'package:flutter/src/material/slider.dart': Failed assertion: line 166 pos 15: 'value >= min && value <= max': is not true.
My code
Expanded(
child: Slider(
activeColor: Color(0xffe7ad29),
inactiveColor: Color(0xFF707070),
value: model.playerBarValue,
onChanged: (val) {
model.seekFromBar(val);
},
),
),
class PlayerProvider extends ChangeNotifier {
final player = AssetsAudioPlayer();
String link;
Duration playerTimeNow = Duration(seconds: 0);
Duration playerLength;
double playerBarValue = 0.0;
Episode episode;
Item podcastInfo;
String episodeName, episodeThumbnail;
bool isPlaying = false;
PlayerProvider() {
updateState();
}
play() async {
print("Started Playing");
// Stop previous playing
player.stop();
playerTimeNow = Duration(seconds: 0);
isPlaying = false;
// link = updateLinkToHttps(link);
print(link);
final audio = Audio.network(
link,
metas: Metas(
title: podcastInfo.collectionName,
artist: podcastInfo.artistName,
album: podcastInfo.trackName,
image: MetasImage.network(podcastInfo.artworkUrl600),
//can be MetasImage.network
),
);
var duration = await player.open(
audio,
showNotification: true,
notificationSettings: NotificationSettings(
//seekBarEnabled: false,
//stopEnabled: true,
//customStopAction: (player){
// player.stop();
//}
//prevEnabled: false,
customNextAction: (player) {
print("next1");
forward();
}, customPrevAction: (player) {
print("next2");
backword();
}
//customStopIcon: AndroidResDrawable(name: "ic_stop_custom"),
//customPauseIcon: AndroidResDrawable(name:"ic_pause_custom"),
//customPlayIcon: AndroidResDrawable(name:"ic_play_custom"),
),
);
isPlaying = true;
// player.play(); // Usually you don't want to wait for playback to finish.
print("started");
setState();
}
pause() async {
await player.pause();
isPlaying = false;
print("paused");
setState();
}
resume() async {
//TODO: Setup resume
await player.seek(playerTimeNow);
player.play();
isPlaying = true;
}
speed(double val) async {
print(val);
//TODO: Setup resume
await player.setPlaySpeed(val);
isPlaying = true;
}
updateState() {
player.currentPosition.listen((event) {
playerTimeNow = event;
updatePlayerBar();
});
}
updatePlayerBar() {
int totalLengthInMilliSeconds = playerLength.inMilliseconds;
int totalPlayedInMilliSeconds = playerTimeNow.inMilliseconds;
double newPlayerBarValue =
totalPlayedInMilliSeconds / totalLengthInMilliSeconds;
playerBarValue = newPlayerBarValue;
// print(playerBarValue);
// print(playerTimeNow);
// print(playerLength);
// print(playerLength);
// if (playerLength == playerTimeNow) {
// print('Finish');
// player.stop();
// }
notifyListeners();
}
forward() async {
//TODO: Check if at-least 10 seconds are left;
if (playerTimeNow + Duration(seconds: 10) < playerLength)
await player.seek(playerTimeNow + Duration(seconds: 10));
else
await player.seek(playerLength);
print("Forwarded 10 seconds");
}
backword() async {
Duration back = playerTimeNow.inSeconds > 10
? playerTimeNow - Duration(seconds: 10)
: Duration(seconds: 0);
await player.seek(back);
print("Backwarded 10 seconds");
}
seekFromBar(double val) async {
double totalMillis = playerLength.inMilliseconds * val;
int newMillis = totalMillis.toInt();
Duration newSeekLocations = Duration(milliseconds: newMillis);
await player.seek(newSeekLocations);
print("Seek from Bar");
}
setState() {
notifyListeners();
}
}
When time is finished of player then it's showing this error on red screen. I need to know the fix of this? Mean when it's finished time go to 0 or something. The issue is on the slider I think because if I back from the red screen then my slider goes to zero.

check thet the value of model.playerBarValue is neither Nan or null, and set a max value for the slider.
Slider(
value: model.playerBarValue.isNaN==true || model.playerBarValue==null? 0 : model.playerBarValue,
min: 0.0,
max: duration.inSeconds.toDouble() + 1.0,
onChanged: (value) {
. . .
},
)

Related

The method 'openAudioSession' isn't defined for the type 'FlutterSoundPlayer'

Please help
I'm using the following in dependencies:
flutter_sound: ^9.2.13
and i did an import of :
import 'package:flutter_sound/flutter_sound.dart';
but im getting that error
The method 'openAudioSession' isn't defined for the type 'FlutterSoundPlayer'. (Documentation) Try correcting the name to the name of an existing method, or defining a method named 'openAudioSession'.
here is the screenshot
Here is the code:
class _VoicePlayer extends StatefulWidget {
final String trackUrl;
final String fileName;
const _VoicePlayer(
{Key key, #required this.trackUrl, #required this.fileName})
: super(key: key);
#override
_VoicePlayerState createState() => _VoicePlayerState();
}
class _VoicePlayerState extends State<_VoicePlayer> {
final FlutterSoundPlayer _myPlayer = FlutterSoundPlayer();
bool _isPlay = false;
String _errorMsg = '';
bool _canPlay = false;
Duration _recordDuration = Duration(milliseconds: 1);
Duration _playPosition = Duration(milliseconds: 0);
StreamSubscription<Duration> _playerSubscription = null;
String _msg = '';
//Track track;
#override
void initState() {
super.initState();
_myPlayer.openAudioSession().then((value) {
//print('_myPlayer value --> $value');
setState(() {
_canPlay = true;
});
});
}
#override
void dispose() {
if (_playerSubscription != null) {
_playerSubscription.cancel();
_playerSubscription = null;
}
_myPlayer.closeAudioSession();
super.dispose();
}
Stream<Duration> _streamPlayerProgress(Duration recordDurationInSec) {
StreamController<Duration> controller;
Timer timer;
int counter = 500;
void runProgress(_) {
var curDuration = Duration(milliseconds: counter);
if (recordDurationInSec >= (curDuration)) {
controller.add(curDuration);
//counter += 111;
counter += 500;
} else {
timer.cancel();
timer = null;
//print('timer completed !');
}
}
void startTimer() {
timer = Timer.periodic(const Duration(milliseconds: 500), runProgress);
}
void stopTimer() {
if (timer != null) {
timer.cancel();
timer = null;
}
if (controller != null) {
controller.close();
controller = null;
}
}
controller =
StreamController<Duration>(onListen: startTimer, onCancel: stopTimer);
return controller.stream;
}
Future<void> _startStopPlayNew(bool isPlay) async {
if (_canPlay) {
if (isPlay) {
if (_myPlayer != null) {
await _myPlayer.stopPlayer();
if (_myPlayer.isStopped) {
setState(() {
_isPlay = false;
_playPosition = Duration(milliseconds: 0);
if (_playerSubscription != null) {
_playerSubscription.cancel();
_playerSubscription = null;
}
});
}
}
//print('stop track --> ${widget.trackUrl}');
} else {
//print('play track --> ${widget.trackUrl}');
Duration d = await _myPlayer.startPlayer(
fromURI: widget.trackUrl,
whenFinished: () {
//print('player finished playing !');
setState(() {
_isPlay = false;
_playPosition = Duration(milliseconds: 0);
if (_playerSubscription != null) {
_playerSubscription.cancel();
_playerSubscription = null;
}
});
},
);
if (_myPlayer.isPlaying) {
setState(() {
_msg = '';
_recordDuration = d;
_playerSubscription =
_streamPlayerProgress(_recordDuration).listen((e) {
//print('current progress --> $e');
setState(() {
_playPosition = e;
});
});
_isPlay = true;
});
}
}
} else {
setState(() {
_errorMsg = 'Cannot play audio';
});
}
}
ElevatedButton _togglePlayButton(bool isPlay) => ElevatedButton(
onPressed: () async {
if (!isPlay && _canPlay && _errorMsg.isEmpty) {
//print('Play track !');
setState(() {
_msg = 'Loading...';
});
_startStopPlayNew(isPlay);
//_startStopPlay(isPlay);
//setState(() {
// _isPlay = true;
//});
} else {
if (_canPlay && _errorMsg.isEmpty) {
//print('Stop play track !');
_startStopPlayNew(isPlay);
}
//_startStopPlay(isPlay);
//setState(() {
// _isPlay = false;
//});
}
},
child: isPlay
? const Icon(Icons.stop_rounded, color: Colors.white)
: const Icon(Icons.play_arrow_rounded, color: Colors.white),
style: ButtonStyle(
backgroundColor: isPlay
? MaterialStateProperty.all<Color>(Colors.cyan)
: MaterialStateProperty.all<Color>(Colors.green[400]),
shape:
MaterialStateProperty.all<OutlinedBorder>(RoundedRectangleBorder(
borderRadius: BorderRadius.all(Radius.circular(8)),
)),
),
);

Flutter- Android - App crash When Using faceDetector on imageStream

whenever I use the app with face detector in debug, profile, or release mode it works fine but when i build the app and install it then start it the app automatically close after the camera stream starts
im using google_ml_kit: ^0.7.3 and camera: ^0.9.4+14
this is the code i use to initialize the camera and start detecting every time
void initCamera() async {
final description = await availableCameras().then(
(cameras) => cameras.firstWhere(
(camera) => camera.lensDirection == CameraLensDirection.front,
),
);
cameraControllerNotifier.value = CameraController(
description,
ResolutionPreset.low,
enableAudio: false,
);
await cameraControllerNotifier.value!.initialize();
await Future.delayed(const Duration(milliseconds: 500));
isDetecting = false;
cameraControllerNotifier.value!.startImageStream((img) async {
if (isDetecting) return;
if (cameraControllerNotifier.value != null) {
isDetecting = true;
final image = InputImage.fromBytes(
bytes: img.planes[0].bytes,
inputImageData: InputImageData(
inputImageFormat:
InputImageFormatMethods.fromRawValue(img.format.raw)!,
size: Size(img.width.toDouble(), img.height.toDouble()),
imageRotation: MlHelper.rotationIntToImageRotation(
description.sensorOrientation,
),
planeData: null,
),
);
try {
final faceDetector = GoogleMlKit.vision.faceDetector(
const FaceDetectorOptions(
mode: FaceDetectorMode.accurate,
enableLandmarks: true,
),
);
List<Face> _faces = await faceDetector.processImage(image);
if (_faces.isNotEmpty) {
//..........
} else {
isClose.value = false;
}
isDetecting = false;
// facesNotifier.value = _faces;
} catch (e) {
isClose.value = false;
isDetecting = false;
log("FaceKIt Error : $e");
}
}
});
if (mounted) {
setState(() {});
}
}

flutter how to terminate all ongoing actions when the back button is pressed?

I want to terminate any currently executing function task when the back button is clicked.How can I do it?(I want to terminate the below function if I press back button)
void getData(String locale, String searchKey, List<String> contentType,
int categoryID, int start, int limit) async {
print('get data');
temp = (await context.read(knowledgeBaseViewModelProvider).getCategoryData(
locale, searchKey, contentType, categoryID, start, limit))!;
_isLoding = false;
if(mounted){
setState(() {
if (temp.length == 0 ) {
isEnd = true;
momAlertBox(
context,
"Alert",
"No More Data.Try Another Category!",
"Oky.",
() => Navigator.pop(context, 'OK'),
);
} else {
isEnd = false;
}
isLodingState = false;
items.addAll(temp);
});
}
}
The back button
BackButton(
onPress: () => {
Navigator.pop(context)},
svgAssetsPath: "assets/icons/icon_back.svg",
height: SizeConfig.devicePixelRatio * 8,
width: SizeConfig.devicePixelRatio * 8,
),

In flutter how can we use audio_service to fetch dynamic data

await AudioService.start(
backgroundTaskEntrypoint: _audioPlayerTaskEntrypoint,
androidNotificationChannelName: 'Audio Player',
androidNotificationColor: 0xFF2196f3,
androidNotificationIcon: 'mipmap/ic_launcher',
params: getParams(),
);
This is my code snippet where i am calling AudioService.start but i am unable to start service.
i am fetching the audio item from firebase and want to load those as a list view to audio_service..But i am unable to do that.My class where i have defined a audio service extending the background service.
import 'package:audio_service/audio_service.dart';
import 'package:just_audio/just_audio.dart';
MediaControl playControl = MediaControl(
androidIcon: 'drawable/ic_action_play_arrow',
label: 'Play',
action: MediaAction.play,
);
MediaControl pauseControl = MediaControl(
androidIcon: 'drawable/ic_action_pause',
label: 'Pause',
action: MediaAction.pause,
);
MediaControl skipToNextControl = MediaControl(
androidIcon: 'drawable/ic_action_skip_next',
label: 'Next',
action: MediaAction.skipToNext,
);
MediaControl skipToPreviousControl = MediaControl(
androidIcon: 'drawable/ic_action_skip_previous',
label: 'Previous',
action: MediaAction.skipToPrevious,
);
MediaControl stopControl = MediaControl(
androidIcon: 'drawable/ic_action_stop',
label: 'Stop',
action: MediaAction.stop,
);
class AudioPlayerTask extends BackgroundAudioTask {
//
var _queue = <MediaItem>[];
int _queueIndex = -1;
AudioPlayer _audioPlayer = new AudioPlayer();
AudioProcessingState _skipState;
bool _playing;
bool get hasNext => _queueIndex + 1 < _queue.length;
bool get hasPrevious => _queueIndex > 0;
MediaItem get mediaItem => _queue[_queueIndex];
StreamSubscription<AudioPlaybackState> _playerStateSubscription;
StreamSubscription<AudioPlaybackEvent> _eventSubscription;
#override
void onStart(Map<String, dynamic> params) {
print("-------------------------------------started");
_queue.clear();
List mediaItems = params['data'];
for (int i = 0; i < mediaItems.length; i++) {
MediaItem mediaItem = MediaItem.fromJson(mediaItems[i]);
_queue.add(mediaItem);
}
_playerStateSubscription = _audioPlayer.playbackStateStream
.where((state) => state == AudioPlaybackState.completed)
.listen((state) {
_handlePlaybackCompleted();
});
_eventSubscription = _audioPlayer.playbackEventStream.listen((event) {
final bufferingState =
event.buffering ? AudioProcessingState.buffering : null;
switch (event.state) {
case AudioPlaybackState.paused:
_setState(
processingState: bufferingState ?? AudioProcessingState.ready,
position: event.position);
break;
case AudioPlaybackState.playing:
_setState(
processingState: bufferingState ?? AudioProcessingState.ready,
position: event.position);
break;
case AudioPlaybackState.connecting:
_setState(
processingState: _skipState ?? AudioProcessingState.connecting,
position: event.position);
break;
default:
}
});
AudioServiceBackground.setQueue(_queue);
onSkipToNext();
}
#override
void onPlay() {
if (_skipState == null) {
_playing = true;
_audioPlayer.play();
}
}
#override
void onPause() {
_playing = false;
_audioPlayer.pause();
}
#override
void onSkipToNext() async {
skip(1);
}
#override
void onSkipToPrevious() {
skip(-1);
}
void skip(int offset) async {
int newPos = _queueIndex + offset;
if (!(newPos >= 0 && newPos < _queue.length)) {
return;
}
if (null == _playing) {
_playing = true;
} else if (_playing) {
await _audioPlayer.stop();
}
_queueIndex = newPos;
_skipState = offset > 0
? AudioProcessingState.skippingToNext
: AudioProcessingState.skippingToPrevious;
AudioServiceBackground.setMediaItem(mediaItem);
await _audioPlayer.setUrl(mediaItem.id);
print(mediaItem.id);
_skipState = null;
if (_playing) {
onPlay();
} else {
_setState(processingState: AudioProcessingState.ready);
}
}
#override
Future<void> onStop() async {
_playing = false;
await _audioPlayer.stop();
await _audioPlayer.dispose();
_playerStateSubscription.cancel();
_eventSubscription.cancel();
return await super.onStop();
}
#override
void onSeekTo(Duration position) {
_audioPlayer.seek(position);
}
#override
void onClick(MediaButton button) {
playPause();
}
#override
Future<void> onFastForward() async {
await _seekRelative(fastForwardInterval);
}
#override
Future<void> onRewind() async {
await _seekRelative(rewindInterval);
}
Future<void> _seekRelative(Duration offset) async {
var newPosition = _audioPlayer.playbackEvent.position + offset;
if (newPosition < Duration.zero) {
newPosition = Duration.zero;
}
if (newPosition > mediaItem.duration) {
newPosition = mediaItem.duration;
}
await _audioPlayer.seek(_audioPlayer.playbackEvent.position + offset);
}
_handlePlaybackCompleted() {
if (hasNext) {
onSkipToNext();
} else {
onStop();
}
}
void playPause() {
if (AudioServiceBackground.state.playing)
onPause();
else
onPlay();
}
Future<void> _setState({
AudioProcessingState processingState,
Duration position,
Duration bufferedPosition,
}) async {
print('SetState $processingState');
if (position == null) {
position = _audioPlayer.playbackEvent.position;
}
await AudioServiceBackground.setState(
controls: getControls(),
systemActions: [MediaAction.seekTo],
processingState:
processingState ?? AudioServiceBackground.state.processingState,
playing: _playing,
position: position,
bufferedPosition: bufferedPosition ?? position,
speed: _audioPlayer.speed,
);
}
List<MediaControl> getControls() {
if (_playing) {
return [
skipToPreviousControl,
pauseControl,
stopControl,
skipToNextControl
];
} else {
return [
skipToPreviousControl,
playControl,
stopControl,
skipToNextControl
];
}
} this is my class
}
class AudioState {
final List<MediaItem> queue;
final MediaItem mediaItem;
final PlaybackState playbackState;
AudioState(this.queue, this.mediaItem, this.playbackState);
}
You should overridthis method inAudioPlayerTask` class:
#override
// ignore: missing_return
Future<Function> onAddQueueItem(MediaItem mediaItem) async{
// queue.add(mediaItem); or somthing like this to update your queue
await AudioServiceBackground.setQueue(queue);
try {
await _player.load(ConcatenatingAudioSource(
children:
queue.map((item) => AudioSource.uri(Uri.parse(item.id))).toList(),
));
// In this example, we automatically start playing on start.
onPlay();
} catch (e) {
print("Error: $e");
onStop();
}
}
Then you can call this function in your UI:
await AudioService.start(
backgroundTaskEntrypoint: audioPlayerTaskEntrypoint,
androidNotificationChannelName:
'Audio Service Demo',
// Enable this if you want the Android service to exit the foreground state on pause.
//androidStopForegroundOnPause: true,
androidNotificationColor: 0xFF2196f3,
androidNotificationIcon: 'mipmap/ic_launcher',
androidEnableQueue: true,
);
// call this func:
await AudioService.addQueueItem(m);
According to the author here the plugin originally didn't allow passing any arguments to the background task directly. It was designed to let the background task internally query what to play from internal storage via SQLite or tools like shared_preferences.
However today, the plugin allows to pass media data down to the background task via 3 different ways that I identified:
AudioService.addQueueItem(item) combined with onAddQueueItem as mentioned in the above answer as well as this one
AudioService.customAction('url', url) combined with onCustomAction as explained here
Use the Map<String, dynamic> params argument of the AudioService.start method. It is received as an argument of the background task's onStart method as explained here

type 'future<dynamic>' is not a subtype of type 'function'

when i run my app in debug mode it shows me the error "type 'future' is not a subtype of type 'function'" all over the screen and also in the debug console. Can someone help me? I imagine it's a problem with async functions "reset","rateoGet" and "rateoSave" but i can't find any solution.
P.S. I've deleted part of the code because it was useless for this question.
int plus;
int min;
int per;
int div;
double val;
int gameswon =0;
int moves;
static int mosse=15;
String win = "gioca";
int games=0;
double rateo=1;
String mode;
int flag;
var timer=30;
#override
void initState() {
super.initState();
reset();
}
#override
Widget build(BuildContext context) {
return Scaffold(
body:
MyButton(text: "$per" ,color: Colors.deepPurpleAccent, onTap: (){
setState(() {
val*=per;
});
if(widget.mode=="timermode" && flag==0){
timerceckresults();
}else if(widget.mode=="movesmode"){
checkResult();
}
},
MyBottomButton(text: "Reset",color: Colors.indigo,width:160, onTap: reset()),
),
}
checkResult() {
if(val == 101) {
print("hai vinto");
win="Hai Vinto";
setState(() {});
gameswon++;
Timer(Duration(seconds: 2), () {
reset();
});
} else {
print("ci sei quasi");
moves++;
mosse--;
win="$mosse moves left";
setState(() {});
if(moves>14){
print("hai perso coglione");
win="Hai Perso Coglione";
setState(() {});
Timer(Duration(seconds: 2), () {
reset();
});
}
}
}
timerceckresults(){
flag=1;
timer = 30;
Timer.periodic(Duration(seconds: 1), (t){
timer--;
setState(() {
win = "${timer.toString()}seconds left";
});
if(val==101){
timer=0;
}
if(timer == 0) {
t.cancel();
if(val == 101) {
win="Hai Vinto";
setState(() {});
gameswon++;
Timer(Duration(seconds: 2), () {
reset();
});
} else {
win="Hai Perso Coglione";
setState(() {});
Timer(Duration(seconds: 2), () {
reset();
});
}
}
});
static int randNum(x,y) {
var rng = new Random();
return rng.nextInt(y-x)+x;
}
reset() async{
timer=1;
plus = randNum(4, 9);
min = randNum(5, 19);
per = randNum(3, 9);
div = randNum(2, 5);
val = randNum(2, 11).toDouble();
moves = 0;
mosse=15;
if(widget.mode=="timermode"){
win="start playing";
}else{
win="$mosse moves left";
}
await rateoSave();
await rateoGet();
games++;
rateo=gameswon/(games-1);
await rateoSave();
flag=0;
setState(() {});
}
rateoSave() async {
SharedPreferences prefs=await SharedPreferences.getInstance();
await prefs.setInt("games",games);
await prefs.setInt("gameswon",gameswon);
}
rateoGet() async {
SharedPreferences prefs=await SharedPreferences.getInstance();
games=(prefs.getInt("games") ?? 0);
gameswon=(prefs.getInt("gameswon") ?? 0);
https://dart.dev/codelabs/async-await read this before you check the answer will help you alot
reset() async{
timer=1;
plus = randNum(4, 9);
min = randNum(5, 19);
per = randNum(3, 9);
div = randNum(2, 5);
val = randNum(2, 11).toDouble();
moves = 0;
mosse=15;
if(widget.mode=="timermode"){
win="start playing";
}else{
win="$mosse moves left";
}
await rateoSave();
await rateoGet();
games++;
rateo=gameswon/(games-1);
await rateoSave();
flag=0;
setState(() {});
}
Future<bool> rateoSave() {
SharedPreferences prefs= SharedPreferences.getInstance();
prefs.setInt("games",games);
prefs.setInt("gameswon",gameswon);
return true;
}
Future<bool> rateoGet() async {
SharedPreferences prefs= SharedPreferences.getInstance();
await games=(prefs.getInt("games") ?? 0);
await gameswon=(prefs.getInt("gameswon") ?? 0);
return true;
}
you are trying to get a variable from a method that returns a future. you need to add await just before you make the call to that function.
can you tell us in which line this error occurs ?
The most important thing to keep in mind is that if anything in your call-chain returns a Future, everything above it must deal with futures, either by returning the future itself (if no processing must be done), or await'ing and dealing with the returned value (but you'll still be returning a future).