Android 评级栏 : handler for same star tapped as current rating?

标签 android

我正在开发一个RatingBar(作为“星条”)实现,虽然我使用onRatingChanged()委托(delegate)方法让它运行得很好,但有一个明显的遗漏(或我只是盲目的东西)在 API 中:只有当评级实际改变时才会触发这个事件,而不是当用户点击已经设置的同一个星星时触发。

例如,如果我在评级栏中显示 3/5 星级,则点击 2 或 5 组会触发 onRatingChanged(),但点击 3 组绝对不会执行任何操作。

我正在捕获 onTouch 并允许它传播(用于其他自定义 UI 目的),但我当然没有关于点击哪颗星星的引用。如果我这样做了,我可以将其与当前的 getRating() 进行比较并处理“相同的星星点击”情况。

还有其他人尝试完成此任务,或者对我可以探索的其他方法有任何提示吗?我已经在RatingBar层次结构中上下移动了,但没有看到任何有用的东西。理想情况下,onRatingChanged()只会以相同的评级触发,我可以在那里处理它。 :/

谢谢。

更新

感谢下面的 Bas van Stein,我最终使用了 Runnable 来延迟触摸事件处理程序的 ACTION_UP 检查中当前与新评级检查的执行。它并不漂亮,但似乎确实有效(设备上待定)。请记住,这是 RatingBar 本身的子类实现:

@Override
public boolean onTouch(View v, MotionEvent event) {
    // we only want to handle this on DOWN or MOVE (drag)
    int action = event.getAction();

    if(action == MotionEvent.ACTION_DOWN || action == MotionEvent.ACTION_MOVE) {
        Log.d(TAG, "Starbar touched; current rating=" + getRating());

        // do stuff for UI purposes here

        // capture the current rating before onRatingChanged does anything    
        currentRating = getRating();
    }

    if(action == MotionEvent.ACTION_UP) {

        Handler handler = new Handler(Looper.getMainLooper());
        final Runnable r = new Runnable() {
            public void run() {
                float newRating = getRating();

                if(currentRating == newRating) {
                    Log.d(TAG, "Same rating tapped; would unrate");
                    // do something UI related here
                } else {
                    Log.d(TAG, "New rating, will just show it");
                    // this just falls through to my onRatingChanged()
                }
            }
        };

        handler.postDelayed(r, (long) 0.1);
    }

    // allow the touch event to propagate
    return false;
}

最佳答案

您实际上确实知道正在按下哪个评级,因为这始终是触摸事件开始(touch_down)时的当前评级。

评级更改函数将在两个触摸事件之后调用,因此您应该做的是检查触摸操作开始时的评级ACTION_DOWN以及触摸操作结束后的评级 >ACTION_UP。如果两者相同,您就知道已给出相同的评级(当前评级),如果它已更改,您的 onChangeRating 监听器将捕获它。

private current_rating = 0;
ratingBar.setOnTouchListener(new OnTouchListener() {
    @Override
    public boolean onTouch(View v, MotionEvent event) {
        if (event.getAction() == MotionEvent.ACTION_DOWN) {
            current_rating = ratingBar.getRating()
        }
        if (event.getAction() == MotionEvent.ACTION_UP) {
            final Handler handler = new Handler();
            handler.postDelayed(new Runnable() {
              @Override
              public void run() {
                 if (current_rating == ratingBar.getRating() ){
                     //touched but no change between down and up, so fire the same rating.
                 }
              }
            }, 100);
        }
        return true;
    }
});

关于Android 评级栏 : handler for same star tapped as current rating?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/45110109/

相关文章:

java - Android 启动画面不显示

android - 从 Android 中的 ListView 和数据库中删除一个项目

android - 在 Android 中制作文本转语音包装器

java - 无法在我的 Android 设备上获取经度和纬度

java - 调用包含 "#"的号码

java - 有没有办法在Java类中使用gradle变量

java - 在 android 中实现旋转锁定

android - E/Android运行时: FATAL EXCEPTION: main and Coroutine,改造2

java - 如何在Java中使用非标准变量名来生成XML标签?

java - 我的 Firebase 数据库中的数据被覆盖。如何修复它?