Titanium JIRA Archive
Titanium SDK/CLI (TIMOB)

[TIMOB-15829] Android: Calling Ti.UI.Android.ProgressIndicator.hide() twice crashes app on next show()

GitHub Issuen/a
TypeBug
PriorityLow
StatusClosed
ResolutionFixed
Resolution Date2019-04-29T14:54:32.000+0000
Affected Version/sRelease 3.1.1
Fix Version/sRelease 8.0.1
ComponentsAndroid
LabelsSupportTeam, android, progressindicator, reprod
ReporterFokke Zandbergen
AssigneeJoshua Quick
Created2013-08-30T15:15:06.000+0000
Updated2019-04-29T14:54:32.000+0000

Description

If you call hide() twice on a ProgressIndicator *positioned in the status bar* the next time you call show() it will crash. Why I call hide() twice? Because multiple independent processes share a single (indeterminant) ProgressIndicator and call hide() not (needing) knowing what the others did before him.

Steps to reproduce

Create an app: titanium create -p android -n testProgress --id test.progress

Use the following code for app.js:

    Ti.UI.backgroundColor = 'white';

    var win = Ti.UI.createWindow({
      backgroundColor: 'blue'
    });

    var button = Ti.UI.createButton({
      title: 'Show Progress Dialog'
    });

    var progressIndicator = Ti.UI.Android.createProgressIndicator({
      message: 'Loading...',
      location: Ti.UI.Android.PROGRESS_INDICATOR_STATUS_BAR,
      type: Ti.UI.Android.PROGRESS_INDICATOR_DETERMINANT,
      cancelable: true,
      min: 0,
      max: 10
    });

    button.addEventListener('click', function (e) {
      progressIndicator.show();
      var value = 0;
      setInterval(function(){
        if (value > 10) {
            return;
        }
        progressIndicator.value = value;
        value ++;
      }, 200);
      // do some work that takes 3 seconds
      // ie. replace the following setTimeout block with your code
      setTimeout(function(){
        progressIndicator.hide();
        progressIndicator.hide();
      }, 3000);
    });

    win.add(button);
    win.open();
    

Build it to a device: titanium build -p android -T device

Press the button and wait for the progress indicator to finish

Press the button again and watch the app crash and spit out the following log:

09-10 20:50:13.027: E/TiApplication(5497): (main) [10239,10239] Sending event: exception on thread: main msg:java.lang.NullPointerException; Titanium 3.1.3,2013/09/08 09:51,b8f209a
    09-10 20:50:13.027: E/TiApplication(5497): java.lang.NullPointerException
    09-10 20:50:13.027: E/TiApplication(5497):  at ti.modules.titanium.ui.widget.TiUIProgressIndicator.handleShow(TiUIProgressIndicator.java:187)
    09-10 20:50:13.027: E/TiApplication(5497):  at ti.modules.titanium.ui.widget.TiUIProgressIndicator.show(TiUIProgressIndicator.java:144)
    09-10 20:50:13.027: E/TiApplication(5497):  at ti.modules.titanium.ui.android.ProgressIndicatorProxy.handleShow(ProgressIndicatorProxy.java:62)
    09-10 20:50:13.027: E/TiApplication(5497):  at org.appcelerator.titanium.proxy.TiViewProxy.handleMessage(TiViewProxy.java:233)
    09-10 20:50:13.027: E/TiApplication(5497):  at android.os.Handler.dispatchMessage(Handler.java:95)
    09-10 20:50:13.027: E/TiApplication(5497):  at android.os.Looper.loop(Looper.java:137)
    09-10 20:50:13.027: E/TiApplication(5497):  at android.app.ActivityThread.main(ActivityThread.java:4921)
    09-10 20:50:13.027: E/TiApplication(5497):  at java.lang.reflect.Method.invokeNative(Native Method)
    09-10 20:50:13.027: E/TiApplication(5497):  at java.lang.reflect.Method.invoke(Method.java:511)
    09-10 20:50:13.027: E/TiApplication(5497):  at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1027)
    09-10 20:50:13.027: E/TiApplication(5497):  at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:794)
    09-10 20:50:13.027: E/TiApplication(5497):  at dalvik.system.NativeStart.main(Native Method)
    09-10 20:50:13.082: E/AndroidRuntime(5497): FATAL EXCEPTION: main
    09-10 20:50:13.082: E/AndroidRuntime(5497): java.lang.NullPointerException
    09-10 20:50:13.082: E/AndroidRuntime(5497):     at ti.modules.titanium.ui.widget.TiUIProgressIndicator.handleShow(TiUIProgressIndicator.java:187)
    09-10 20:50:13.082: E/AndroidRuntime(5497):     at ti.modules.titanium.ui.widget.TiUIProgressIndicator.show(TiUIProgressIndicator.java:144)
    09-10 20:50:13.082: E/AndroidRuntime(5497):     at ti.modules.titanium.ui.android.ProgressIndicatorProxy.handleShow(ProgressIndicatorProxy.java:62)
    09-10 20:50:13.082: E/AndroidRuntime(5497):     at org.appcelerator.titanium.proxy.TiViewProxy.handleMessage(TiViewProxy.java:233)
    09-10 20:50:13.082: E/AndroidRuntime(5497):     at android.os.Handler.dispatchMessage(Handler.java:95)
    09-10 20:50:13.082: E/AndroidRuntime(5497):     at android.os.Looper.loop(Looper.java:137)
    09-10 20:50:13.082: E/AndroidRuntime(5497):     at android.app.ActivityThread.main(ActivityThread.java:4921)
    09-10 20:50:13.082: E/AndroidRuntime(5497):     at java.lang.reflect.Method.invokeNative(Native Method)
    09-10 20:50:13.082: E/AndroidRuntime(5497):     at java.lang.reflect.Method.invoke(Method.java:511)
    09-10 20:50:13.082: E/AndroidRuntime(5497):     at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1027)
    09-10 20:50:13.082: E/AndroidRuntime(5497):     at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:794)
    09-10 20:50:13.082: E/AndroidRuntime(5497):     at dalvik.system.NativeStart.main(Native Method)
    

Comments

  1. Mauro Parra-Miranda 2013-09-10

    Tried this: ~~~ Ti.UI.backgroundColor = 'white'; var win = Ti.UI.createWindow({ backgroundColor: 'blue' }); var button = Ti.UI.createButton({ title: 'Show Progress Dialog' }); var progressIndicator = Ti.UI.Android.createProgressIndicator({ message: 'Loading...', location: Ti.UI.Android.PROGRESS_INDICATOR_DIALOG, type: Ti.UI.Android.PROGRESS_INDICATOR_DETERMINANT, cancelable: true, min: 0, max: 10 }); button.addEventListener('click', function (e) { progressIndicator.show(); var value = 0; setInterval(function(){ if (value > 10) { return; } progressIndicator.value = value; value ++; }, 200); // do some work that takes 3 seconds // ie. replace the following setTimeout block with your code setTimeout(function(){ progressIndicator.hide(); progressIndicator.hide(); }, 5000); }); win.add(button); win.open(); ~~~ didn't crash or complain. Tested in Nexus 4, Android OS 4.3 Best, Mauro
  2. Fokke Zandbergen 2013-09-10

    [~mpmiranda], did you even read the steps I laid out? The code you use does not locate the progressIndicator in the status bar and does not call hide() twice before calling show() again. I've updated the steps, including the exact code and crash logs. Why call hide() twice? Because it shouldn't be a problem firs of all, but also because often (in my humble experience) a progress indicator is used by several processes each able to hide/show it independent of each other. They shouldn't not need to keep track of the current state.
  3. Fokke Zandbergen 2013-11-26

    [~mpmiranda] Why just close this issue without even taking the effort of responding to my comment?
  4. Mauro Parra-Miranda 2013-11-26

    Hello Fokke! I haven't been able to reproduce this in my personal device. I will try to find a S2 in the office, so I can test this in the same device than you. Thanks for your help, Mauro
  5. Lee Morris 2017-07-11

    I am able to reproduce this issue with the following environment; Pixel (7.1) Studio 4.9.0.201705302345 Ti SDK 6.1.1 GA Appc NPM 4.2.9 Appc CLI 6.2.2 Ti CLI 5.0.14 Alloy 1.9.11 Xcode 8.2 (8C38) Node v4.8.2 Java 1.8.0_131 This is the error I see; [WARN] : W/System.err: java.lang.NullPointerException: Attempt to invoke interface method 'java.lang.String java.lang.CharSequence.toString()' on a null object reference [WARN] : W/System.err: at ti.modules.titanium.ui.widget.TiUIProgressIndicator.handleShow(TiUIProgressIndicator.java:189) [WARN] : W/System.err: at ti.modules.titanium.ui.widget.TiUIProgressIndicator.show(TiUIProgressIndicator.java:146) [WARN] : W/System.err: at ti.modules.titanium.ui.android.ProgressIndicatorProxy.handleShow(ProgressIndicatorProxy.java:57) [WARN] : W/System.err: at org.appcelerator.titanium.proxy.TiViewProxy.show(TiViewProxy.java:788) [WARN] : W/System.err: at ti.modules.titanium.ui.TiDialogProxy.access$001(TiDialogProxy.java:22) [WARN] : W/System.err: at ti.modules.titanium.ui.TiDialogProxy$1.onCurrentActivityReady(TiDialogProxy.java:40) [WARN] : W/System.err: at org.appcelerator.titanium.util.TiUIHelper.waitForCurrentActivity(TiUIHelper.java:186) [WARN] : W/System.err: at ti.modules.titanium.ui.TiDialogProxy.show(TiDialogProxy.java:35) [WARN] : W/System.err: at org.appcelerator.kroll.runtime.v8.V8Object.nativeFireEvent(Native Method) [WARN] : W/System.err: at org.appcelerator.kroll.runtime.v8.V8Object.fireEvent(V8Object.java:62) [WARN] : W/System.err: at org.appcelerator.kroll.KrollProxy.doFireEvent(KrollProxy.java:872) [WARN] : W/System.err: at org.appcelerator.kroll.KrollProxy.handleMessage(KrollProxy.java:1095) [WARN] : W/System.err: at org.appcelerator.titanium.proxy.TiViewProxy.handleMessage(TiViewProxy.java:360) [WARN] : W/System.err: at android.os.Handler.dispatchMessage(Handler.java:98) [WARN] : W/System.err: at android.os.Looper.loop(Looper.java:154) [WARN] : W/System.err: at android.app.ActivityThread.main(ActivityThread.java:6119) [WARN] : W/System.err: at java.lang.reflect.Method.invoke(Native Method) [WARN] : W/System.err: at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:886) [WARN] : W/System.err: at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:776) [ERROR] : TiExceptionHandler: (main) [37883,37883] ----- Titanium Javascript Runtime Error ----- [ERROR] : TiExceptionHandler: (main) [1,37884] - In /app.js:21,25 [ERROR] : TiExceptionHandler: (main) [0,37884] - Message: Uncaught Attempt to invoke interface method 'java.lang.String java.lang.CharSequence.toString()' on a null object reference [ERROR] : TiExceptionHandler: (main) [0,37884] - Source: progressIndicator.show(); [ERROR] : V8Exception: Exception occurred at /app.js:21: Uncaught Attempt to invoke interface method 'java.lang.String java.lang.CharSequence.toString()' on a null object reference [ERROR] : V8Exception: Attempt to invoke interface method 'java.lang.String java.lang.CharSequence.toString()' on a null object reference
  6. Joshua Quick 2019-04-12

    PR (master): https://github.com/appcelerator/titanium_mobile/pull/10829
  7. Joshua Quick 2019-04-26

    PR (8.0.x): https://github.com/appcelerator/titanium_mobile/pull/10868
  8. Lokesh Choudhary 2019-04-26

    FR passed PR merged.
  9. Samir Mohammed 2019-04-29

    Closing ticket, fix verified in SDK version 8.0.1.v20190426162041 and SDK version 8.1.0.v20190426222341. Test and other information can be found at: Master : https://github.com/appcelerator/titanium_mobile/pull/10829 8_0_X: https://github.com/appcelerator/titanium_mobile/pull/10868

JSON Source