有两种建议的方法可用于解释和使用来自环境光传感器的照度数据。
- 对数据应用转换,以便可以将标准化光照水平按照直接比例用于程序行为或交互。 例如,一个示例是根据规范化数据(或与户外环境相关的规范化数据范围)动态调整程序中按钮的大小。 此方法提供了最佳实现。
- 处理不同范围的照度数据,并将程序行为和反应映射到这些范围的上限和下限阈值。 这是响应照明条件的简单方法,可能不会产生最佳的用户体验。 但是,如果平滑转换不可行,此方法会正常工作。
处理来自多个光传感器的数据
若要生成当前照明条件最准确的近似值,可以使用来自多个环境光传感器的数据。 由于环境光传感器可以部分或完全遮盖住覆盖传感器的阴影或物体,因此多个传感器相隔一些距离可以提供比单个传感器更好的当前照明条件的近似值。
若要跟踪来自多个传感器的数据,可以使用以下两种方法:
- 可以保留每个环境光传感器的最新数据值,以及每个读数的传感器数据报告中的时间戳。 为每个传感器读取保留最后一次收到的 ISensorDataReport,并且这可以为日后的参考提供两个值。 通过引用每个传感器数据报告的时间戳,可以根据数据年龄管理数据。 例如,如果数据超过 2 秒,可以省略它。 根据较新的传感器数据值,可以使用最高读数,因为假定相应的传感器不会被遮盖。
- 可以使用最后一次报告的环境光传感器值。 此实现不是最佳实现,因为多个传感器的值不会相互比较以获取最准确的结果。 不建议使用此方法。
示例代码
以下示例代码演示 OnDataUpdated 事件的实现。 事件处理程序调用名为 UpdateUI 的帮助程序函数,该函数会根据照度值更改用户界面。 编写 UpdateUI 的实现由你负责。
// Override of ISensorEvents::OnDataUpdated
// Part of an event sink implementation for ISensorEvents
STDMETHODIMP CALSEventSink::OnDataUpdated(
ISensor* pSensor,
ISensorDataReport* pNewData)
{
HRESULT hr = S_OK;
if(pSensor == NULL ||
pNewData == NULL)
{
return E_POINTER;
}
// Declare and initialize the PROPVARIANT
PROPVARIANT lightLevel;
PropVariantInit(&lightLevel);
// Get the sensor reading from the ISensorDataReport object
hr = pNewData->GetSensorValue(
SENSOR_DATA_TYPE_LIGHT_LEVEL_LUX,
&lightLevel);
if(SUCCEEDED(hr))
{
if(lightlevel.vt == VT_R4)
{
// Extract the float value from the PROPVARIANT object
float luxValue = lightLevel.fltVal;
// Normalize the light sensor data
double lightNormalized = ::log10(luxValue) / 5.0;
// Handle UI changes based on the normalized LUX data
// which ranges from 0.0 - 1.0 for a lux range of
// 0 lux to 100,000 lux.
UpdateUI(lightNormalized);
}
}
// Release the variant.
PropVariantClear(&lightLevel);
return hr;
}