不会调用Drawable类的OnDraw()方法

时间:2016-05-29 11:22:09

标签: android android-drawable ondraw

我已尝试在线提供所有可能的功能,但此方法并未一致地调用。有时会调用onDraw()方法,有时只是忽略它: 请帮助我,任何帮助表示赞赏; BadgeDrawable类:(想要在操作栏中的通知图标上绘制徽章)

public class BadgeDrawable extends Drawable {

private float mTextSize;
private Paint mBadgePaint;
private Paint mBadgePaint1;
private Paint mTextPaint;
private Rect mTxtRect = new Rect();

private String mCount = "";
private boolean mWillDraw = false;

public BadgeDrawable(Context context) {
    mTextSize = /*context.getResources().getDimension(R.dimen.badge_text_size)*/ 20;
    mBadgePaint = new Paint();
    mBadgePaint.setColor(ResourceReader.getInstance(context).getColorFromResource(R.color.colorPrimary));
    mBadgePaint.setAntiAlias(true);
    mBadgePaint.setStyle(Paint.Style.FILL);
    mBadgePaint1 = new Paint();
    mBadgePaint1.setColor(Color.parseColor("#FFFFFF"));//white
    mBadgePaint1.setAntiAlias(true);
    mBadgePaint1.setStyle(Paint.Style.FILL);

    mTextPaint = new Paint();
    mTextPaint.setColor(Color.WHITE);
    mTextPaint.setTypeface(Typeface.DEFAULT);
    mTextPaint.setTextSize(mTextSize);
    //mTextPaint.setFlags(Paint.FAKE_BOLD_TEXT_FLAG);
    mTextPaint.setAntiAlias(true);
    mTextPaint.setTextAlign(Paint.Align.CENTER);
    this.setCallback(callback);
}

@Override
public void draw(Canvas canvas) {

    Log.d("dj", "onDraw BadgeDrawable");
    if (!mWillDraw) {
        return;
    }

    Rect bounds = getBounds();
    float width = bounds.right - bounds.left;
    float height = bounds.bottom - bounds.top;
    float radius = ((Math.max(width, height) / 2)) / 2;
    float centerX = (width - radius - 1) +10;
    float centerY = radius -5;
    if(mCount.length() <= 2){
        // Draw badge circle.
        /*canvas.drawCircle(centerX, centerY, radius+9, mBadgePaint1);
        canvas.drawCircle(centerX, centerY, radius+7, mBadgePaint);*/

        canvas.drawCircle(centerX, centerY, radius+9, mBadgePaint1);
        canvas.drawCircle(centerX, centerY, radius+7, mBadgePaint);
    }
    else{
        /*canvas.drawCircle(centerX, centerY, radius+10, mBadgePaint1);
        canvas.drawCircle(centerX, centerY, radius+8, mBadgePaint);*/

        canvas.drawCircle(centerX, centerY, radius+10, mBadgePaint1);
        canvas.drawCircle(centerX, centerY, radius+8, mBadgePaint);
    }
    // Draw badge count text inside the circle.
    mTextPaint.getTextBounds(mCount, 0, mCount.length(), mTxtRect);
    float textHeight = mTxtRect.bottom - mTxtRect.top;
    float textY = centerY + (textHeight / 2f);
    /*if(mCount.length() > 2)
    canvas.drawText("99+", centerX, textY, mTextPaint);
    else*/
    canvas.drawText(mCount, centerX, textY, mTextPaint);
}

/*
 Sets the count (i.e notifications) to display.
  */
public void setCount(String count) {
    Log.d(Constants.TAG, "setCount count val- BadgeDrawable: "+count);
    mCount = count;
    // Only draw a badge if there are notifications.
    mWillDraw = !count.equalsIgnoreCase("0");
    invalidateSelf();
}


private Drawable.Callback callback = new Callback() {
    @Override
    public void invalidateDrawable(Drawable who) {
        Log.d(Constants.TAG, "invalidateDrawable - BadgeDrawable: ");
    }

    @Override
    public void scheduleDrawable(Drawable who, Runnable what, long when) {

    }

    @Override
    public void unscheduleDrawable(Drawable who, Runnable what) {

    }
};

@Override
public void setAlpha(int alpha) {
    // do nothing
}

@Override
public void setColorFilter(ColorFilter cf) {
    // do nothing
}

@Override
public int getOpacity() {
    return PixelFormat.UNKNOWN;
}

}

因此,当我从服务器获得未读通知的计数时,我设置如下:

public static void setBadgeCount(Context context, LayerDrawable icon, String count) {

    BadgeDrawable badge; // Reuse drawable if possible
    Drawable reuse = icon.findDrawableByLayerId(R.id.ic_badge); //getting the layer 2
    if (reuse != null && reuse instanceof BadgeDrawable) {
        badge = (BadgeDrawable) reuse;
    } else {
        badge = new BadgeDrawable(context);
    }
    badge.setCount(count);
    icon.mutate();
    icon.setDrawableByLayerId(R.id.ic_badge, badge);
}

2 个答案:

答案 0 :(得分:1)

我知道为时已晚。答案是

public static void setBadgeCount(Context context, LayerDrawable icon, String count) {

BadgeDrawable badge; // Reuse drawable if possible
Drawable reuse = icon.findDrawableByLayerId(R.id.ic_badge); //getting the layer 2
if (reuse != null && reuse instanceof BadgeDrawable) {
    badge = (BadgeDrawable) reuse;
} else {
    badge = new BadgeDrawable(context);
    icon.mutate();
    icon.setDrawableByLayerId(R.id.ic_badge, badge);
}

badge.setCount(count);

}

答案 1 :(得分:0)

确保drawable的边界产生的宽度和高度大于0.当drawable的绑定宽度或高度为0时,将不会调用draw方法

您可以通过在drawable本身上调用setBounds()来设置drawable的边界。

修改

使drawable重绘自己的另一种方法是使用级别机制。这对于动画的绘图很有用,但无论如何都可以使用。

您可以通过调用:

来触发drawable的刷新
setLevel(getLevel() + 1)

此外,如果您希望drawable在级别更改时重绘,则需要覆盖以下方法并返回true:

@Override
protected boolean onLevelChange(int level) {
    return true;
}

也许您甚至可以考虑使用关卡而不是&#34; count&#34;变量,因为如果级别没有改变,则不会触发重绘。

希望这有帮助。