@@ -50,7 +50,10 @@ class PriceWidget : AppWidgetProvider() {
5050 var appWidgetMaxWidth : Int? = null ,
5151 var appWidgetMaxHeight : Int? = null ,
5252 // Cache chart to redraw on size changes
53- var cachedChart : List <Array <Double >> = listOf()
53+ var cachedChart : List <Array <Double >> = listOf(),
54+ var cachedChartDt : Long = 0 ,
55+ var cachedChartCurrency : String? = null ,
56+ var isShown : Boolean = false
5457 ) {
5558 constructor (config: JSONObject ? ) : this (
5659 token = config?.optJSONObject(" token" ),
@@ -82,7 +85,10 @@ class PriceWidget : AppWidgetProvider() {
8285 }
8386 }
8487 chartList
85- }()
88+ }(),
89+ cachedChartDt = config?.optLong(" cachedChartDt" ) ? : 0 ,
90+ cachedChartCurrency = config?.optString(" cachedChartCurrency" ),
91+ isShown = config?.optBoolean(" isShown" ) ? : false ,
8692 )
8793
8894 fun toJson (): JSONObject =
@@ -99,6 +105,9 @@ class PriceWidget : AppWidgetProvider() {
99105 }
100106 }
101107 put(" cachedChart" , JSONArray (chartArray))
108+ put(" cachedChartDt" , cachedChartDt)
109+ put(" cachedChartCurrency" , cachedChartCurrency)
110+ put(" isShown" , isShown)
102111 }
103112
104113 val tokenChain: String?
@@ -177,37 +186,52 @@ class PriceWidget : AppWidgetProvider() {
177186 appWidgetManager,
178187 appWidgetId,
179188 config,
180- WBaseStorage .getBaseCurrency()
181189 )
182190 }
183191 }
184192
185193 override fun onUpdate (
186194 context : Context ,
187195 appWidgetManager : AppWidgetManager ,
188- appWidgetIds : IntArray
196+ appWidgetIds : IntArray ,
197+ ) {
198+ updateAppWidgets(context, appWidgetManager, appWidgetIds, null )
199+ }
200+
201+ fun updateAppWidgets (
202+ context : Context ,
203+ appWidgetManager : AppWidgetManager ,
204+ appWidgetIds : IntArray ,
205+ onCompletion : (() -> Unit )?
189206 ) {
190207 val cachedPriceChartData = mutableMapOf<String , Array <Array <Double >>>()
191208 ApplicationContextHolder .update(context.applicationContext)
192209 WBaseStorage .init (context)
193210 val baseCurrency = WBaseStorage .getBaseCurrency() ? : MBaseCurrency .USD
194211 val widgetQueue: Queue <Int > = LinkedList (appWidgetIds.toList())
195212
213+ // TODO:: Consider loading parallel since it's not common to have several widgets with same token and period.
214+ // Make sure to don't miss onCompletion?.invoke() if changed anything!
196215 fun processNextWidget () {
197- val appWidgetId = widgetQueue.poll() ? : return
216+ val appWidgetId = widgetQueue.poll() ? : run {
217+ onCompletion?.invoke()
218+ return
219+ }
198220
199221 var config = Config (WBaseStorage .getWidgetConfigurations(appWidgetId) ? : JSONObject ())
200222 if (config.appWidgetMinWidth == null || config.appWidgetMinHeight == null ) {
201223 val options = appWidgetManager.getAppWidgetOptions(appWidgetId)
202- config.appWidgetMinWidth =
203- options.getInt(AppWidgetManager .OPTION_APPWIDGET_MIN_WIDTH )
204- config.appWidgetMinHeight =
205- options.getInt(AppWidgetManager .OPTION_APPWIDGET_MIN_HEIGHT )
206- config.appWidgetMaxWidth =
207- options.getInt(AppWidgetManager .OPTION_APPWIDGET_MAX_WIDTH )
208- config.appWidgetMaxHeight =
209- options.getInt(AppWidgetManager .OPTION_APPWIDGET_MAX_HEIGHT )
210- WBaseStorage .setWidgetConfigurations(appWidgetId, config.toJson())
224+ val minWidth = options.getInt(AppWidgetManager .OPTION_APPWIDGET_MIN_WIDTH )
225+ if (minWidth > 0 ) {
226+ config.appWidgetMinWidth = minWidth
227+ config.appWidgetMinHeight =
228+ options.getInt(AppWidgetManager .OPTION_APPWIDGET_MIN_HEIGHT )
229+ config.appWidgetMaxWidth =
230+ options.getInt(AppWidgetManager .OPTION_APPWIDGET_MAX_WIDTH )
231+ config.appWidgetMaxHeight =
232+ options.getInt(AppWidgetManager .OPTION_APPWIDGET_MAX_HEIGHT )
233+ WBaseStorage .setWidgetConfigurations(appWidgetId, config.toJson())
234+ }
211235 }
212236 val period = config.period
213237 val cacheKey = " ${config.assetId} _$period "
@@ -223,23 +247,28 @@ class PriceWidget : AppWidgetProvider() {
223247 appWidgetManager,
224248 appWidgetId,
225249 config,
226- baseCurrency
227250 )
228251 processNextWidget()
229252 } ? : run {
230253 val period = config.period?.value ? : run {
231254 processNextWidget()
232255 return
233256 }
234- if (config.cachedChart.isEmpty()) {
235- // Show loading widget
257+ // Update with latest chart data available if base currencies match
258+ if (config.cachedChartCurrency == baseCurrency.currencyCode)
236259 updateAppWidget(
237260 context,
238261 appWidgetManager,
239262 appWidgetId,
240263 config,
241- baseCurrency
242264 )
265+ // Ignore requesting again if it's updated less than a minute ago
266+ if (config.cachedChart.isNotEmpty() &&
267+ config.cachedChartDt > System .currentTimeMillis() - 60_000 &&
268+ config.cachedChartCurrency == baseCurrency.currencyCode
269+ ) {
270+ processNextWidget()
271+ return
243272 }
244273 val assetId = config.assetId ? : DEFAULT_TOKEN
245274 SDKApiMethod .Token .PriceChart (
@@ -253,6 +282,8 @@ class PriceWidget : AppWidgetProvider() {
253282 config =
254283 Config (WBaseStorage .getWidgetConfigurations(appWidgetId)).apply {
255284 cachedChart = result.toList()
285+ cachedChartDt = System .currentTimeMillis()
286+ cachedChartCurrency = baseCurrency.currencyCode
256287 }
257288 if (config.assetId != assetId || config.period?.value != period) {
258289 processNextWidget()
@@ -264,7 +295,6 @@ class PriceWidget : AppWidgetProvider() {
264295 appWidgetManager,
265296 appWidgetId,
266297 config,
267- baseCurrency
268298 )
269299 processNextWidget()
270300 }
@@ -284,10 +314,24 @@ class PriceWidget : AppWidgetProvider() {
284314 appWidgetManager : AppWidgetManager ,
285315 appWidgetId : Int ,
286316 config : Config ,
287- baseCurrency : MBaseCurrency ? = null,
288317 ) {
289318 val orientation = context.resources.configuration.orientation
290319 val isLandscape = orientation == Configuration .ORIENTATION_LANDSCAPE
320+ if (! config.isShown) {
321+ config.isShown = true
322+ WBaseStorage .setWidgetConfigurations(appWidgetId, config.toJson())
323+ appWidgetManager.updateAppWidget(
324+ appWidgetId,
325+ generateRemoteViews(
326+ context,
327+ config,
328+ if (isLandscape) config.appWidgetMaxWidth else config.appWidgetMinWidth,
329+ if (isLandscape) config.appWidgetMinHeight else config.appWidgetMaxHeight,
330+ null ,
331+ appWidgetId
332+ )
333+ )
334+ }
291335 ImageUtils .loadBitmapFromUrl(
292336 context,
293337 config.token?.optString(" image" , " " ),
@@ -297,7 +341,6 @@ class PriceWidget : AppWidgetProvider() {
297341 generateRemoteViews(
298342 context,
299343 config,
300- baseCurrency,
301344 if (isLandscape) config.appWidgetMaxWidth else config.appWidgetMinWidth,
302345 if (isLandscape) config.appWidgetMinHeight else config.appWidgetMaxHeight,
303346 image,
@@ -311,7 +354,6 @@ class PriceWidget : AppWidgetProvider() {
311354 private fun generateRemoteViews (
312355 context : Context ,
313356 config : Config ,
314- baseCurrency : MBaseCurrency ? ,
315357 width : Int? ,
316358 height : Int? ,
317359 image : Bitmap ? ,
@@ -328,6 +370,7 @@ class PriceWidget : AppWidgetProvider() {
328370 )
329371
330372 // PREPARE VALUES //////////////////////////////////////////////////////////////////////////
373+ val baseCurrency = config.cachedChartCurrency?.let { MBaseCurrency .parse(it) }
331374 val priceChartData = config.cachedChart.toTypedArray()
332375 val baseColor = config.token?.optString(" color" , DEFAULT_COLOR )?.toColorInt()
333376 ? : DEFAULT_COLOR .toColorInt()
@@ -495,17 +538,18 @@ class PriceWidget : AppWidgetProvider() {
495538 height : Int? ,
496539 isCompact : Boolean
497540 ) {
498- views.setImageViewBitmap(
499- R .id.chart,
500- ChartUtils .chartToBitmap(
501- context,
502- priceChartData,
503- baseColor = baseColor,
504- chartWidth = width?.dp ? : 200 .dp,
505- chartHeight = (height?.dp ? : 180 .dp) - 130 .dp,
506- paddingBottom = if (isCompact) 77 .dp else 68 .dp
541+ if (width != null && height != null )
542+ views.setImageViewBitmap(
543+ R .id.chart,
544+ ChartUtils .chartToBitmap(
545+ context,
546+ priceChartData,
547+ baseColor = baseColor,
548+ chartWidth = width.dp,
549+ chartHeight = height.dp - 130 .dp,
550+ paddingBottom = if (isCompact) 77 .dp else 68 .dp
551+ )
507552 )
508- )
509553 }
510554
511555 override fun onDeleted (context : Context , appWidgetIds : IntArray? ) {
0 commit comments