为什么我在尝试更新我的个人资料图片时遇到此错误?
Why im getting this error trying to update my profile picture?
大家好,我在 flutter 中尝试更新个人资料图片时遇到错误。
I/BitmapCropTask(22569): Should crop: true
E/flutter (22569): [ERROR:flutter/lib/ui/ui_dart_state.cc(186)] Unhandled Exception: setState() called after dispose(): _MeinAccountState#51c31(lifecycle state: defunct, not mounted)
E/flutter (22569): This error happens if you call setState() on a State object for a widget that no longer appears in the widget tree (e.g., whose parent widget no longer includes the widget in its build). This error can occur when code calls setState() from a timer or an animation callback.
E/flutter (22569): The preferred solution is to cancel the timer or stop listening to the animation in the dispose() callback. Another solution is to check the "mounted" property of this object before calling setState() to ensure the object is still in the tree.
E/flutter (22569): This error might indicate a memory leak if setState() is being called because another object is retaining a reference to this State object after it has been removed from the tree. To avoid memory leaks, consider breaking the reference to this object during dispose().
E/flutter (22569): #0 State.setState.<anonymous closure> (package:flutter/src/widgets/framework.dart:1054:9)
E/flutter (22569): #1 State.setState (package:flutter/src/widgets/framework.dart:1089:6)
E/flutter (22569): #2 _MeinAccountState._cropImage (package:projectandroidstudiodenya/seitenleiste/meinacount.dart:464:7)
E/flutter (22569): <asynchronous suspension>
E/flutter (22569):
I/OpenGLRenderer(22569): Davey! duration=900ms; Flags=1, IntendedVsync=404683725160222, Vsync=404683808493552, OldestInputEvent=9223372036854775807, NewestInputEvent=0, HandleInputStart=404683823245510, AnimationStart=404683823373510, PerformTraversalsStart=404683823679510, DrawStart=404684494965510, SyncQueued=404684496166510, SyncStart=404684547432510, IssueDrawCommandsStart=404684555113510, SwapBuffers=404684565824510, FrameCompleted=404684677131510, DequeueBufferDuration=43941000, QueueBufferDuration=55381000, GpuCompleted=0,
I/OpenGLRenderer(22569): Davey! duration=1032ms; Flags=1, IntendedVsync=404683725160222, Vsync=404683808493552, OldestInputEvent=9223372036854775807, NewestInputEvent=0, HandleInputStart=404683823245510, AnimationStart=404683823373510, PerformTraversalsStart=404683823679510, DrawStart=404684699540510, SyncQueued=404684700293510, SyncStart=404684783237510, IssueDrawCommandsStart=404684795352510, SwapBuffers=404684822351510, FrameCompleted=404684840233510, DequeueBufferDuration=1873000, QueueBufferDuration=12800000, GpuCompleted=470041226614272,
但我没有在 class 中使用计时器。
我的代码很长,所以请告诉我您是否需要大约 400 行的孔代码,或者您是否需要精确的代码
我觉得问题可能出在她身上,因为在我尝试让用户上传图片之前一切正常。
class MeinAccount extends StatefulWidget {
static const route = '/MeinAccount';
@override
_MeinAccountState createState() => _MeinAccountState();
}
class _MeinAccountState extends State<MeinAccount> {
File _pickedImage;
final picker = ImagePicker();
Future _loadPicker(ImageSource source) async {
final picked = await picker.getImage(source: source);
if (this.mounted) { // This checks if the widget is still in the tree
setState(() {
setState(() {
if (picked != null) {
_cropImage(picked);
} else {
print('No image selected.');
}
});
Navigator.pop(context);
});
}
}
_cropImage(PickedFile picked) async {
File cropped = await ImageCropper.cropImage(
sourcePath: picked.path,
aspectRatioPresets: [
CropAspectRatioPreset.original,
CropAspectRatioPreset.ratio16x9,
CropAspectRatioPreset.ratio5x4
],
maxWidth: 800,
);
if (cropped != null) {
setState(() {
_pickedImage = cropped;
});
}
}
void _showPickOptionsDialog(BuildContext context) {
showDialog(
context: context,
builder: (context) => AlertDialog(
content: Column(
mainAxisSize: MainAxisSize.min,
children: <Widget>[
ListTile(
title: Text("Pick from Gallery"),
onTap: () {
_loadPicker(ImageSource.gallery);
},
),
ListTile(
title: Text("Take a picture"),
onTap: () {
_loadPicker(ImageSource.camera);
},
)
],
),
),
);
}
这是错误:
if (cropped != null) {
setState(() {
_pickedImage = cropped;
});
}
错误消失了,但现在显示的是这样
D/MediaScannerConnection(26319): Scanned /storage/emulated/0/Android/data/DENYAGROUP2021.com/files/Pictures/7d96cd78-0a82-47f0-b27d-96246635bc682265191042833866810.jpg to null
D/EGL_emulation(26319): eglCreateContext: 0xf0caca10: maj 3 min 0 rcv 3
D/BitmapLoadUtils(26319): maxBitmapSize: 2792
D/BitmapWorkerTask(26319): Uri scheme: file
I/OpenGLRenderer(26319): Davey! duration=1158ms; Flags=1, IntendedVsync=412117758196194, Vsync=412118108196180, OldestInputEvent=9223372036854775807, NewestInputEvent=0, HandleInputStart=412118118324710, AnimationStart=412118118404710, PerformTraversalsStart=412118151854710, DrawStart=412118706779710, SyncQueued=412118724588710, SyncStart=412118746374710, IssueDrawCommandsStart=412118747987710, SwapBuffers=412118918505710, FrameCompleted=412118938578710, DequeueBufferDuration=696000, QueueBufferDuration=8362000, GpuCompleted=411534615855710,
I/Choreographer(26319): Skipped 53 frames! The application may be doing too much work on its main thread.
I/OpenGLRenderer(26319): Davey! duration=1014ms; Flags=0, IntendedVsync=412118724868043, Vsync=412119608201341, OldestInputEvent=9223372036854775807, NewestInputEvent=0, HandleInputStart=412119616194710, AnimationStart=412119616351710, PerformTraversalsStart=412119617536710, DrawStart=412119625786710, SyncQueued=412119634157710, SyncStart=412119642144710, IssueDrawCommandsStart=412119642624710, SwapBuffers=412119673457710, FrameCompleted=412119747758710, DequeueBufferDuration=3320000, QueueBufferDuration=12352000, GpuCompleted=411534824754710,
D/TransformImageView(26319): Image size: [960:1280]
I/BitmapCropTask(26319): Should crop: false
``
简而言之,由于 async/await 的恶作剧,您的小部件已不在树中。
一个简单的解决方法是使用以下方法检查您的小部件是否在树中:
if (this.mounted) { // This checks if the widget is still in the tree
setState(() {
// [YOUR CODE HERE]
});
}
试试这个:
if (cropped != null) {
if (this.mounted) { // This check whether the state object is in tree
setState(() {
_pickedImage = cropped;
});
}
}
大家好,我在 flutter 中尝试更新个人资料图片时遇到错误。
I/BitmapCropTask(22569): Should crop: true
E/flutter (22569): [ERROR:flutter/lib/ui/ui_dart_state.cc(186)] Unhandled Exception: setState() called after dispose(): _MeinAccountState#51c31(lifecycle state: defunct, not mounted)
E/flutter (22569): This error happens if you call setState() on a State object for a widget that no longer appears in the widget tree (e.g., whose parent widget no longer includes the widget in its build). This error can occur when code calls setState() from a timer or an animation callback.
E/flutter (22569): The preferred solution is to cancel the timer or stop listening to the animation in the dispose() callback. Another solution is to check the "mounted" property of this object before calling setState() to ensure the object is still in the tree.
E/flutter (22569): This error might indicate a memory leak if setState() is being called because another object is retaining a reference to this State object after it has been removed from the tree. To avoid memory leaks, consider breaking the reference to this object during dispose().
E/flutter (22569): #0 State.setState.<anonymous closure> (package:flutter/src/widgets/framework.dart:1054:9)
E/flutter (22569): #1 State.setState (package:flutter/src/widgets/framework.dart:1089:6)
E/flutter (22569): #2 _MeinAccountState._cropImage (package:projectandroidstudiodenya/seitenleiste/meinacount.dart:464:7)
E/flutter (22569): <asynchronous suspension>
E/flutter (22569):
I/OpenGLRenderer(22569): Davey! duration=900ms; Flags=1, IntendedVsync=404683725160222, Vsync=404683808493552, OldestInputEvent=9223372036854775807, NewestInputEvent=0, HandleInputStart=404683823245510, AnimationStart=404683823373510, PerformTraversalsStart=404683823679510, DrawStart=404684494965510, SyncQueued=404684496166510, SyncStart=404684547432510, IssueDrawCommandsStart=404684555113510, SwapBuffers=404684565824510, FrameCompleted=404684677131510, DequeueBufferDuration=43941000, QueueBufferDuration=55381000, GpuCompleted=0,
I/OpenGLRenderer(22569): Davey! duration=1032ms; Flags=1, IntendedVsync=404683725160222, Vsync=404683808493552, OldestInputEvent=9223372036854775807, NewestInputEvent=0, HandleInputStart=404683823245510, AnimationStart=404683823373510, PerformTraversalsStart=404683823679510, DrawStart=404684699540510, SyncQueued=404684700293510, SyncStart=404684783237510, IssueDrawCommandsStart=404684795352510, SwapBuffers=404684822351510, FrameCompleted=404684840233510, DequeueBufferDuration=1873000, QueueBufferDuration=12800000, GpuCompleted=470041226614272,
但我没有在 class 中使用计时器。 我的代码很长,所以请告诉我您是否需要大约 400 行的孔代码,或者您是否需要精确的代码 我觉得问题可能出在她身上,因为在我尝试让用户上传图片之前一切正常。
class MeinAccount extends StatefulWidget {
static const route = '/MeinAccount';
@override
_MeinAccountState createState() => _MeinAccountState();
}
class _MeinAccountState extends State<MeinAccount> {
File _pickedImage;
final picker = ImagePicker();
Future _loadPicker(ImageSource source) async {
final picked = await picker.getImage(source: source);
if (this.mounted) { // This checks if the widget is still in the tree
setState(() {
setState(() {
if (picked != null) {
_cropImage(picked);
} else {
print('No image selected.');
}
});
Navigator.pop(context);
});
}
}
_cropImage(PickedFile picked) async {
File cropped = await ImageCropper.cropImage(
sourcePath: picked.path,
aspectRatioPresets: [
CropAspectRatioPreset.original,
CropAspectRatioPreset.ratio16x9,
CropAspectRatioPreset.ratio5x4
],
maxWidth: 800,
);
if (cropped != null) {
setState(() {
_pickedImage = cropped;
});
}
}
void _showPickOptionsDialog(BuildContext context) {
showDialog(
context: context,
builder: (context) => AlertDialog(
content: Column(
mainAxisSize: MainAxisSize.min,
children: <Widget>[
ListTile(
title: Text("Pick from Gallery"),
onTap: () {
_loadPicker(ImageSource.gallery);
},
),
ListTile(
title: Text("Take a picture"),
onTap: () {
_loadPicker(ImageSource.camera);
},
)
],
),
),
);
}
这是错误:
if (cropped != null) {
setState(() {
_pickedImage = cropped;
});
}
错误消失了,但现在显示的是这样
D/MediaScannerConnection(26319): Scanned /storage/emulated/0/Android/data/DENYAGROUP2021.com/files/Pictures/7d96cd78-0a82-47f0-b27d-96246635bc682265191042833866810.jpg to null
D/EGL_emulation(26319): eglCreateContext: 0xf0caca10: maj 3 min 0 rcv 3
D/BitmapLoadUtils(26319): maxBitmapSize: 2792
D/BitmapWorkerTask(26319): Uri scheme: file
I/OpenGLRenderer(26319): Davey! duration=1158ms; Flags=1, IntendedVsync=412117758196194, Vsync=412118108196180, OldestInputEvent=9223372036854775807, NewestInputEvent=0, HandleInputStart=412118118324710, AnimationStart=412118118404710, PerformTraversalsStart=412118151854710, DrawStart=412118706779710, SyncQueued=412118724588710, SyncStart=412118746374710, IssueDrawCommandsStart=412118747987710, SwapBuffers=412118918505710, FrameCompleted=412118938578710, DequeueBufferDuration=696000, QueueBufferDuration=8362000, GpuCompleted=411534615855710,
I/Choreographer(26319): Skipped 53 frames! The application may be doing too much work on its main thread.
I/OpenGLRenderer(26319): Davey! duration=1014ms; Flags=0, IntendedVsync=412118724868043, Vsync=412119608201341, OldestInputEvent=9223372036854775807, NewestInputEvent=0, HandleInputStart=412119616194710, AnimationStart=412119616351710, PerformTraversalsStart=412119617536710, DrawStart=412119625786710, SyncQueued=412119634157710, SyncStart=412119642144710, IssueDrawCommandsStart=412119642624710, SwapBuffers=412119673457710, FrameCompleted=412119747758710, DequeueBufferDuration=3320000, QueueBufferDuration=12352000, GpuCompleted=411534824754710,
D/TransformImageView(26319): Image size: [960:1280]
I/BitmapCropTask(26319): Should crop: false
``
简而言之,由于 async/await 的恶作剧,您的小部件已不在树中。
一个简单的解决方法是使用以下方法检查您的小部件是否在树中:
if (this.mounted) { // This checks if the widget is still in the tree
setState(() {
// [YOUR CODE HERE]
});
}
试试这个:
if (cropped != null) {
if (this.mounted) { // This check whether the state object is in tree
setState(() {
_pickedImage = cropped;
});
}
}