Android Question How to ensure Page_Created event gets fired for a page when a B4A App is re-invoked immediately after exiting the app with B4XPage_ClosePage ?

beelze69

Active Member
Licensed User
Longtime User
Hi,

I have a b4X Page application with the B4XMainPage invoking another page (say Pg1).

I want some default values to be set when the Pg1 is created due to which I have written the relevant code in the
B4XPage_Created event under Pg1.


I am exiting the app via B4X_CloseRequest with the following code in the B4XMainPage:

B4X:
Private Sub B4XPage_CloseRequest As ResumableSub
    Log("B4x MainPage close event triggered")
 
    Dim cs As CSBuilder
    Dialog.BodyTextColor=xui.Color_White
    Dialog.Title = cs.Initialize.Size(20).Append("Message").PopAll
    Wait For (Dialog.Show("Are you sure?","Yes","No","Cancel" )) Complete ( Result As Int)
    If Result=xui.Dialogresponse_Positive Then
        B4XPages.ClosePage(Me)
        Return(True)
    End If
    Return(False)
 
End Sub

Now, When the end-user exits the Application, due to the Android OS feature, the app still remains in the Cache.

The issue:


In case when the end-user immediately invokes the application again, the B4XPage_Created event does not get fired for pg1 ('cuz for the Android OS the Page is still there in memory).

So how should we ensure that the B4XPage_Created event gets fired EVERYTIME for a page (EVEN in case the end-user suddenly re-invokes a 'previously exited' app but which 'gets invoked from the Cache') ?

Requesting for guidance.

Thanks.
 
Last edited:
  • Like
Reactions: Opa

beelze69

Active Member
Licensed User
Longtime User
The B4XPage_Created event always fires once and it should be so. You can use other page events:
https://www.b4x.com/android/forum/t...or-managing-multiple-pages.118901/post-744867
Hi Lucas,

The issue is that there are some 'default values' of some input parameters which are being set when the Page is first created...Hence the relevant subroutine is called from the Page_Created event.. I have not deliberately put them in the Page_Appear event since i want this default values for that page to be set only once..... However, in this scenario, since android does not remove the program from memory, from the end-user's point of view , he/she has exited the APP but when they visit the same page, their 'OLDER VALUES' are still shown..because the Page_Created event does not get fired .

This will give a very odd feeling to the end-user and technically also, this is not the way any app should behave...

Requesting for help in this regard.
 
Last edited:
Upvote 0

LucaMs

Expert
Licensed User
Longtime User
Hi Lucas,

The issue is that there are some 'default values' of some input parameters which are being set when the Page is first created...Hence the relevant subroutine is called from the Page_Created event.. I have not deliberately put them in the Page_Appear event since i want this default values for that page to be set only once..... However, in this scenario, since android does not remove the program from memory, from the end-user's point of view , he/she has exited the APP but when they visit the same page, their 'OLDER VALUES' are still shown..because the Page_Created event does not get fired .

This will give a very odd feeling to the end-user and technically also, this is not the way any app should behave...

Requesting for help in this regard.
I'm afraid that if you don't give me a concrete example, I won't understand.

If the app is not destroyed, when the user brings it back to the foreground the variables in it will still have their value. If, on the other hand, it is destroyed, the Created event will trigger. So I don't know what the problem is.
 
Upvote 0

Brian Dean

Well-Known Member
Licensed User
Longtime User
In a single activity situation would this do what you want to do ...?

B4X:
Sub Process_Globals
    
End Sub

Sub Globals
    Private closedByUser As Boolean = False
End Sub

Sub Activity_Create(FirstTime As Boolean)
    If FirstTime Then closedByUser = True
End Sub

Sub Activity_Resume
    If closedByUser Then initialiseAppState
End Sub

Sub Activity_Pause (UserClosed As Boolean)
    closedByUser = UserClosed
End Sub

Sub initialiseAppState
    ' Put your initialisation code here
End Sub

If so then maybe @LucaMs can translate this into B4XPages. If this is not what you want then perhaps you can explain exactly what you mean by "the User closes the app". I don't think that your definition is the same as Android's.
 
Upvote 0

Alessandro71

Well-Known Member
Licensed User
Longtime User
I think you can force a proper app close with ExitApplication, but maybe a better solution would be setting the default values again before invoking ClosePage
 
Upvote 0

beelze69

Active Member
Licensed User
Longtime User
I'm afraid that if you don't give me a concrete example, I won't understand.

If the app is not destroyed, when the user brings it back to the foreground the variables in it will still have their value. If, on the other hand, it is destroyed, the Created event will trigger. So I don't know what the problem is.

I think you can force a proper app close with ExitApplication, but maybe a better solution would be setting the default values again before invoking ClosePage
Hi Alessandro71,

But I read in one of the B4A Postings that ExitApplication should not be used ... I was also thinking of the same thing that you said... setting the default values (that I have placed in the Page_Create event) in the routine before I invoke the ClosePage... otherwise, it becomes really awkward for the end-user who sees 'some 'previously changed values' cropping up when he/she has 'properly exited' the app...
 
Upvote 0

beelze69

Active Member
Licensed User
Longtime User
In a single activity situation would this do what you want to do ...?

B4X:
Sub Process_Globals
   
End Sub

Sub Globals
    Private closedByUser As Boolean = False
End Sub

Sub Activity_Create(FirstTime As Boolean)
    If FirstTime Then closedByUser = True
End Sub

Sub Activity_Resume
    If closedByUser Then initialiseAppState
End Sub

Sub Activity_Pause (UserClosed As Boolean)
    closedByUser = UserClosed
End Sub

Sub initialiseAppState
    ' Put your initialisation code here
End Sub

If so then maybe @LucaMs can translate this into B4XPages. If this is not what you want then perhaps you can explain exactly what you mean by "the User closes the app". I don't think that your definition is the same as Android's.
Hi Brian,

Thanks for chipping in..

Let me make it clearer.

I require some 'default values for a particular input field' in a page 'Pg1' (which are set via the Page_Created event)... Now depending on the user-requirement, the end-user can change these default input values in that Page and save the data into a table... Now in the present scenario, despite properly exiting via a 'CloseRequest' .. due to the Android's feature of 'preserving the App in the Cache and revoking it from there', the Page_Create event is never fired... Due to this when the user again views page 'Pg1', he/she sees the 'previously set values shown to him/her' which is not what I want... since the end-user is going to perform a 'totally different operation' on that Page... I hope I have made it clearer now...

Thanks
 
Upvote 0

beelze69

Active Member
Licensed User
Longtime User
I'm afraid that if you don't give me a concrete example, I won't understand.

If the app is not destroyed, when the user brings it back to the foreground the variables in it will still have their value. If, on the other hand, it is destroyed, the Created event will trigger. So I don't know what the problem is.
Hi Lucas,

Thanks for your inputs.

That is where the problem is... I want the App to be destroyed when I invoke the CloseRequest.. but that does not happen ... Android keeps it in the background and the state of the variables are retained .. We cannot change Android Behaviour... All that I want is that when a Page is invoked again after the end-user has exited the app (via a CloseRequest), the Page_Create event should fire so that whatever 'initial values'' I have set there should be again shown to the end-user... I have explained it in more detail in a reply to Brian... I hope I have been more clear this time..

Thanks...
 
Upvote 0

LucaMs

Expert
Licensed User
Longtime User
Create 2 variables at class level, mFirstTime and mClosedByUser, boolean.
Then use B4XPage_Appear.

Class_Globals:
Private mFirstTime, mClosedByUser As Boolean

B4X:
Private Sub B4XPage_Created
    mFirstTime = True
End Sub

B4X:
Private Sub B4XPage_Appear
    If mFirstTime Or mClosedByUser
        InitMe ' <--- call a Sub to set default values or write them here directly.
        mFirstTime = False
        mClosedByUser = False
    End If
    '...
    '...
End Sub

B4X:
Private Sub B4XPage_CloseRequest As ResumableSub
    Dim cs As CSBuilder
    Dialog.BodyTextColor=xui.Color_White
    Dialog.Title = cs.Initialize.Size(20).Append("Message").PopAll
    Wait For (Dialog.Show("Are you sure?","Yes","No","Cancel" )) Complete ( Result As Int)
    If Result=xui.Dialogresponse_Positive Then
        mClosedByUser = True ' <--- added only this one to your code
        B4XPages.ClosePage(Me)
        Return(True)
    End If
    Return(False)
 End Sub
 
Upvote 0

beelze69

Active Member
Licensed User
Longtime User
Create 2 variables at class level, mFirstTime and mClosedByUser, boolean.
Then use B4XPage_Appear.

Class_Globals:
Private mFirstTime, mClosedByUser As Boolean

B4X:
Private Sub B4XPage_Created
    mFirstTime = True
End Sub

B4X:
Private Sub B4XPage_Appear
    If mFirstTime Or mClosedByUser
        InitMe ' <--- call a Sub to set default values or write them here directly.
        mFirstTime = False
        mClosedByUser = False
    End If
    '...
    '...
End Sub

B4X:
Private Sub B4XPage_CloseRequest As ResumableSub
    Dim cs As CSBuilder
    Dialog.BodyTextColor=xui.Color_White
    Dialog.Title = cs.Initialize.Size(20).Append("Message").PopAll
    Wait For (Dialog.Show("Are you sure?","Yes","No","Cancel" )) Complete ( Result As Int)
    If Result=xui.Dialogresponse_Positive Then
        mClosedByUser = True ' <--- added only this one to your code
        B4XPages.ClosePage(Me)
        Return(True)
    End If
    Return(False)
 End Sub
Hi Lucas,

This works for me...

Thank you vey much...
 
Last edited:
Upvote 0

beelze69

Active Member
Licensed User
Longtime User
As Brian indicated above why can't you check the UserClosed parameter in Main.Activity_Pause and set to default if it is true? Maybe call the Page_Create yourself based on this in the Appear or Forground events.
Hi Agraham,

Thanks for your inputs..
Lucas has provided an elegant solution..
On preliminary testing, this seems to work for me..

Thanks..
 
Upvote 0

beelze69

Active Member
Licensed User
Longtime User
In a single activity situation would this do what you want to do ...?

B4X:
Sub Process_Globals
   
End Sub

Sub Globals
    Private closedByUser As Boolean = False
End Sub

Sub Activity_Create(FirstTime As Boolean)
    If FirstTime Then closedByUser = True
End Sub

Sub Activity_Resume
    If closedByUser Then initialiseAppState
End Sub

Sub Activity_Pause (UserClosed As Boolean)
    closedByUser = UserClosed
End Sub

Sub initialiseAppState
    ' Put your initialisation code here
End Sub

If so then maybe @LucaMs can translate this into B4XPages. If this is not what you want then perhaps you can explain exactly what you mean by "the User closes the app". I don't think that your definition is the same as Android's.
Hi Brian,

Thanks a lot for providing the initial idea..
 
Upvote 0

AnandGupta

Expert
Licensed User
Longtime User
Hi @beelze69

Glad that you understood the power and methods of B4XPages. I think you can mark Lucas post as solution.

Actually we are so wired on Android Activity life cycle (this true if you try in AStudio or other Android development tools) that it takes a while to understand power of B4XPages.

I too have faced this dilemma initially, but now use the label/edit etc. value on the page to check for empty (when created) in _Appear and clear the value on Page Close. Simple.
 
Upvote 0
Top