【问题标题】:onProgressChanged() of a SeekBar is called twiceSeekBar 的 onProgressChanged() 被调用两次
【发布时间】:2014-08-14 10:52:37
【问题描述】:

我创建了一个自定义SeekBarPreference,以便它显示一个可供选择的时间范围(比如0.2 秒到2.2 秒)。我的问题是 onProgressChanged() 被调用了两次——一次是progress = 0,第二次是progress = "actual value"。我将值存储在SharedPreference 中,以便稍后在我的应用程序中使用它。
这是我的代码 sn-p -

@Override
protected View onCreateDialogView() {
    LayoutInflater inflator = ((PreferenceActivity) mContext)
            .getLayoutInflater();
    View view = inflator.inflate(R.layout.seek_bar, null);

    mCurrentValue = PreferenceManager.getDefaultSharedPreferences(mContext)
            .getFloat(this.getKey(), mDefaultValue);
    ......
    SeekBar mSeekBar = (SeekBar) view.findViewById(R.id.seekbar);
    mSeekBar.setOnSeekBarChangeListener(this);

    mSeekBar.setMax(20);
    mSeekBar.setProgress((int) ((mCurrentValue - mMinValue)
            / (mMaxValue - mMinValue) * 20)); // 20 = progress bar max value.
    return view;
}

@Override
public void onProgressChanged(SeekBar seekBar, int progress,
        boolean fromUser) {
    if (progress != 0) {
        mCurrentValue = (float) ((float) progress / 20
                * (mMaxValue - mMinValue) + mMinValue);
    }
    mValueText.setText(Float.toString(mCurrentValue)); 
    /* mValueText is a TextBox where I display my Current Value */
}

在这里,我检查了 progress 的值,使其为not equal to 0,因此它避免了第一次调用。但是,这样做的副作用是我无法将任何内容设置为0

有什么办法可以解决这个问题?

【问题讨论】:

    标签: android seekbar preference


    【解决方案1】:

    回调方法onProgressChanged()有一个boolean参数fromUser
    使用此参数,我们可以确定更改是来自框架还是由用户自己做出的。

    因此,像 -

    这样的实现
    @Override
    public void onProgressChanged(SeekBar seekBar, int progress,
            boolean fromUser) {
        if (fromUser) { // If the changes are from the User only then accept the
                        // changes
        /* Instead of -> if (progress != 0) { */
    
            mCurrentValue = (float) ((float) progress / 20
                    * (mMaxValue - mMinValue) + mMinValue);
            mCurrentValue *= 10;
            mCurrentValue = Math.round(mCurrentValue);
            mCurrentValue /= 10;
        }
    
        mValueText.setText(Float.toString(mCurrentValue));
    }
    

    仅当用户更改TextView 的值时才设置它。

    【讨论】:

    • fromUser 救了我的命。
    【解决方案2】:

    您可以使用 OnSeekBarChangeListener 的以下方法。

    public void onStopTrackingTouch(SeekBar seekBar) {
         int progress=seekBar.getProgress();
    
    }
    

    【讨论】:

      【解决方案3】:

      我今天遇到了另一个问题(自定义 SeekBar 和 PreferenceFragment)。我不知道为什么,但下面的代码只工作了两次:开始触摸和停止:

          mTextViewValue = (TextView) view.findViewById(R.id.seekbar_value);
          mSeekBar.setOnSeekBarChangeListener(new SeekBar.OnSeekBarChangeListener() {
              @Override
              public void onProgressChanged(@NonNull SeekBar seekBar, int progress, boolean fromUser) {
                      mTextViewValue.setText(String.valueOf(newValue));
                  }
      

      我终于找到了解决方案。这个有效:

          final TextView valueTextView = (TextView) view.findViewById(R.id.seekbar_value);
          mSeekBar.setOnSeekBarChangeListener(new SeekBar.OnSeekBarChangeListener() {
              @Override
              public void onProgressChanged(@NonNull SeekBar seekBar, int progress, boolean fromUser) {
                      valueTextView.setText(String.valueOf(newValue));
                  }
      

      也许它对某人有帮助。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2013-08-27
        • 2013-09-05
        • 2016-04-01
        相关资源
        最近更新 更多