Problem with clearing the display on the Instinct 2

I'm creating a watch face for the Instinct 2, and I'm having a problem clearing the display. My watch face doesn't use a layout, so I don't call `View.onUpdate()` in my `onUpdate()` function, and instead use `dc.clear()` when I want to clear the display. I only want to clear the display occasionally, so I don't have to redraw everything on the watch face.

I'm finding that, if I make my watch face only call `dc.clear()` once in certain situations, the "subscreen" (the little circular display in the corner) will not be cleared properly - it will be white when the rest of the display is black. This happens when I am viewing the widget glances and then return to the watch face. I'm not sure if I'm doing something wrong, or if this is a bug, so I've included an example watch face based on the default watch face that reproduces the issue.

```

import Toybox.Graphics;
import Toybox.Lang;
import Toybox.System;
import Toybox.WatchUi;

class SubscreenTestView extends WatchUi.WatchFace {

    private var _redraw_all as Boolean;
    private var _prev_time as String;

    function initialize() {
        WatchFace.initialize();
        _redraw_all = true;
        _prev_time = "";
    }

    // Load your resources here
    function onLayout(dc as Dc) as Void {
        // setLayout(Rez.Layouts.WatchFace(dc));
        _redraw_all = true;
    }

    // Called when this View is brought to the foreground. Restore
    // the state of this View and prepare it to be shown. This includes
    // loading resources into memory.
    function onShow() as Void {
        _redraw_all = true;
    }

    // Update the view
    function onUpdate(dc as Dc) as Void {
        // Get and show the current time
        var clockTime = System.getClockTime();
        var timeString = Lang.format("$1$:$2$", [clockTime.hour, clockTime.min.format("%02d")]);

        if(_redraw_all || timeString != _prev_time)
        {
            _prev_time = timeString;
            dc.setColor(Graphics.COLOR_BLACK, Graphics.COLOR_BLACK);
            dc.clear();
            _redraw_all = false;
        }

        var ui_text = new WatchUi.Text({
            :text=>timeString,
            :color=>Graphics.COLOR_WHITE,
            :font=>Graphics.FONT_LARGE,
            :locX =>88,
            :locY=>88,
            :justification=>Graphics.TEXT_JUSTIFY_CENTER
        });
        ui_text.draw(dc);

    }

    // Called when this View is removed from the screen. Save the
    // state of this View here. This includes freeing resources from
    // memory.
    function onHide() as Void {
    }

    // The user has just looked at their watch. Timers and animations may be started here.
    function onExitSleep() as Void {
        _redraw_all = true;
    }

    // Terminate any active timers and prepare for slow updates.
    function onEnterSleep() as Void {
    }

}
```
(Sorry for not using the code insertion tool. It seems like it's not working right now.)
Hopefully someone with more experience can take a look at this and help me figure out what's going on. Thanks in advance!
  • You want to set the colors before the dc.clear() and you always want to update the entire display each time onUpdate is called, so you always want to clear the screen..  With onPartialUpdat you can update part of the display (such as seconds), but that's it  Don't even consider doing that in onUpdate

    With my CIQ watchfaces on an I2, when it's fully charged, I see an estimate of 27-28 days, and see that in usage.

    When you do a dc.clear that will also clear the subscreen, so it must be re-drawn

  • Okay, thanks. I am indeed setting the colors before dc.clear(). 

    Could you elaborate on why you shouldn't update only part of the screen in onUpdate()? I got this idea from this Garmin blog post (see towards the end), so it seems like doing this is officially endorsed in at least one place. 

    My problem is that dc.clear() seemingly does not clear the subscreen properly.

  • First of all, it fails on devices where the screen is cleared before onUpdate is called.  Secondly it fails if you get a notification that only changes part of the screen.

    There are many threads and bug reports here about why updating part of the screen in onUpdate in a watch face is a bad idea.

    In a wf, if you are using direct dc, always clear the screen and update everything when onUpdate is called. If you are using layouts, the entire screen screen is redrawn when you do the View.onUpdate()

  • I see, thanks. That blog post was a little misleading apparently. I'll try using a buffered bitmap instead.

    It's weird that the first dc.clear() call makes the subscreen white instead of black, but I guess that shouldn't matter too much if I call it every time.

  • Why do you need a buffered bitmap? to make the update a tiny bit faster?  If you are refreshing the screen with a buffered bitmap, you're still updating the whole screen and all you save is the calcs needed for a specific item.  For something like steps, you don't was to use what you saved a minute ago, but want to show the current value. 

    You want to keep this as simple as possible.