title: Understanding Android BLE ScanSettings parameters
body: <p>The documentation around <a href="https://developer.android.com/reference/android/bluetooth/le/ScanSettings" rel="noreferrer">ScanSettings</a> is very laconic and I'm having a hard time coming up with an optimal configurations.</p>
  <p>My requirements dictate I should report a new advertisement packet that matches my filter criteria (filtered on service UUIDs) as soon as possible. Duplicate advertisement packets are of no use to me. The advertisement packets will change when the peripheral will register an event on its side and the advertisement packet is thus an opportunity for me to detect changes and act accordingly. I also need to know when the peripheral stopped advertising (powered off or not in range anymore).</p>
  <p>I've tried to set the callback type like following:</p>
  <pre><code>setCallbackType(ScanSettings.CALLBACK_TYPE_FIRST_MATCH | ScanSettings.CALLBACK_TYPE_MATCH_LOST)
  </code></pre>
  <p>The documentation for this parameters says:</p>
  <blockquote>
  <p>int CALLBACK_TYPE_ALL_MATCHES</p>
  <p>Trigger a callback for every Bluetooth advertisement found that matches the filter criteria. If no filter is active, all advertisement packets are reported.</p>
  <p>int CALLBACK_TYPE_FIRST_MATCH</p>
  <p>A result callback is only triggered for the first advertisement packet received that matches the filter criteria.</p>
  <p>int CALLBACK_TYPE_MATCH_LOST</p>
  <p>Receive a callback when advertisements are no longer received from a device that has been previously reported by a first match callback.</p>
  </blockquote>
  <p>I was hoping with this to get notified when the peripheral becomes available and then get notified when the peripheral is lost. However this doesn't trigger any scan results, at least not on my Pixel 2. So I just switched to use <code>CALLBACK_TYPE_ALL_MATCHES</code> and now I get all the advertisement packets. This is probably what I want anyways if I want to get updated packets from the same peripheral.</p>
  <p>I looked at the <code>setMatchMode</code> parameters and it appears that this only configures the callbacks rate based on the signal strength:</p>
  <blockquote>
  <p>int MATCH_MODE_AGGRESSIVE</p>
  <p>In Aggressive mode, hw will determine a match sooner even with feeble signal strength and few number of sightings/match in a duration.</p>
  <p>int MATCH_MODE_STICKY</p>
  <p>For sticky mode, higher threshold of signal strength and sightings is required before reporting by hw</p>
  </blockquote>
  <p>The <code>setNumOfMatches</code> claims to handle the number of advertisements per filter, but none of the documented parameters seem to make a difference, I still get a burst of packets from the same peripheral that didn't change, seemingly at about the same rate no matter the parameter.</p>
  <p>To meet the part of my requirement where I need to determine if the peripheral stopped advertising (powered off or not in range) I came up with a timestamp of last seen packet from the peripheral and determine if the peripheral is lost or not when I don't see a packet for x amount of seconds. This was necessary because the <code>CALLBACK_TYPE_FIRST_MATCH</code> and <code>CALLBACK_TYPE_MATCH_LOST</code> don't seem to work at all.</p>
  <p>This unfortunately means I get bursts of similar packets triggering a chain reaction in my code that I now have to deal with.</p>
  <p>How can I configure the scanning so that I get notified only when the advertisement packet changes or the peripheral stopped advertising? Am I missing something here, or that's just not possible.</p>