如何在XML布局中使用onDraw()?invalidate无法刷新onDraw()函数问题
解决自定义View在XML布局中invalidate()无法触发重绘的问题
嘿,我一眼就看出你问题所在了——你操作的自定义View实例和屏幕上显示的根本不是同一个!
问题根源拆解
你在onCreate()里手动new了一个CircleView,但紧接着加载的是XML布局,屏幕上显示的是XML里创建的那个CircleView实例。后面你调用update()和invalidate()的是自己new的那个没加到界面上的View,当然不会触发屏幕上的View重绘啦!
具体修复步骤
1. 正确获取界面上的CircleView实例
删掉onCreate()里手动new的代码,改成从布局中获取真正显示的实例:
protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_track_map); // 从XML布局中拿到屏幕上的那个CircleView circleView = findViewById(R.id.CircleView); }
2. 修正自定义View的布局参数
你给XML里的CircleView设置了wrap_content,但作为背景地图的View,应该占满整个布局,不然你的圆形绘制可能被限制在很小的区域。改成match_parent:
<com.b143lul.android.logreg.CircleView android:id="@+id/CircleView" android:layout_width="match_parent" android:layout_height="match_parent" android:background="@drawable/resized_track_2" />
3. 确保onDraw依赖更新后的变量
检查你的onDraw()方法,确保它确实使用了groupScores和localUsername来绘制圆形,不然就算触发重绘也看不到变化。可以加个日志验证:
protected void onDraw(Canvas canvas) { super.onDraw(canvas); // 别漏了这个,否则可能影响背景图绘制 Log.d("CircleView", "onDraw触发,当前用户名:" + localUsername); // 你的圆形绘制逻辑... }
4. (可选)确保UI操作在主线程
如果你的update()方法是在网络请求的子线程回调里调用的,记得用postInvalidate()代替invalidate(),它会自动切换到主线程刷新:
public void update(JSONObject allGroupScores, String username) { groupScores = allGroupScores; localUsername = username; postInvalidate(); // 替代invalidate,自动在主线程执行重绘 }
这样改完之后,XML布局的控件和自定义View的动态绘制就能正常共存,绘制内容也会覆盖在地图背景之上啦!
内容的提问来源于stack exchange,提问作者Night
相关产品推荐
相关产品推荐

