Android Question File export ... how to ?

freedom2000

Well-Known Member
Licensed User
Longtime User
Hi,

After reading this post : https://www.b4x.com/android/forum/t...list-of-other-related-methods.129897/#content


I am trying the "saveAs" code to write text into a file

B4X:
Sub SaveAs (Source As InputStream, MimeType As String, Title As String) As ResumableSub
    Dim intent As Intent
    intent.Initialize("android.intent.action.CREATE_DOCUMENT", "")
    intent.AddCategory("android.intent.category.OPENABLE")
    intent.PutExtra("android.intent.extra.TITLE", Title)
    intent.SetType(MimeType)
    StartActivityForResult(intent)
    Wait For ion_Event (MethodName As String, Args() As Object)
    If -1 = Args(0) Then 'resultCode = RESULT_OK
        Dim result As Intent = Args(1)
        Dim jo As JavaObject = result
        Dim ctxt As JavaObject
        Dim ContentResolver As JavaObject = ctxt.InitializeContext.RunMethodJO("getContentResolver", Null)
        Dim out As OutputStream = ContentResolver.RunMethod("openOutputStream", Array(jo.RunMethod("getData", Null), "wt")) 'wt = Write+Trim
        File.Copy2(Source, out)
        out.Close
        Return True
    End If
    Return False
End Sub

Sub StartActivityForResult(i As Intent)
    Dim jo As JavaObject = GetBA
    ion = jo.CreateEvent("anywheresoftware.b4a.IOnActivityResult", "ion", Null)
    jo.RunMethod("startActivityForResult", Array(ion, i))
End Sub

Sub GetBA As Object
    Dim jo As JavaObject
    Dim cls As String = Me
    cls = cls.SubString("class ".Length)
    jo.InitializeStatic(cls)
    Return jo.GetField("processBA")
End Sub

and to use it :

B4X:
Private Sub Export_click
    File.WriteString(File.DirInternal, "test.txt", "test") 'just for the example.

    Wait For (SaveAs(File.OpenInput(File.DirInternal, "test.txt"), "application/octet-stream", "test.txt")) Complete (Success As Boolean)
    Log("File saved successfully? " & Success)
End Sub

This code compiles without issue and runs. I can choose the file name, I can see the created file into the "download" folder.
But when I open the file it is empty, totally empty... the "test" string doesn' appear.

What am I doing wrong ?

BTW I just would like to export a serie of values acquired by my ESP32 to play with them into Excel on my PC. Everything works but the file export !

Thanks
JP
 

teddybear

Well-Known Member
Licensed User
Try changing MimeType to "text/plain",

B4X:
    Wait For (SaveAs(File.OpenInput(File.DirInternal, "test.txt"), "text/plain", "test.txt")) Complete (Success As Boolean)

    Log("File saved successfully? " & Success)
 
Upvote 0

agraham

Expert
Licensed User
Longtime User
I think that I have seen something similar happen to me before. Try a Sleep(100) or thereabouts after the File.Write. Although file writes appear to be synchronous when you look at the underlying Java I suspect that when it gets to the Android API file system access can be asynchronous on occasion. You may be trying to read the file before the contents have been flushed to memory.
 
Upvote 0

freedom2000

Well-Known Member
Licensed User
Longtime User
When looking at the log, I have this error :

Unexpected event (missing RaiseSynchronousEvents): ion_event
Check the unfiltered logs for the full stack trace.

In fact I have this warning :


"undeclared variable ion (warning #8)
 
Upvote 0

freedom2000

Well-Known Member
Licensed User
Longtime User
And here is the unfiltered log :

onProvideContentCaptureStructure(): calling assumeLayout()
onProvideContentCaptureStructure(): calling assumeLayout()
Unexpected event (missing RaiseSynchronousEvents): ion_event
Check the unfiltered logs for the full stack trace.
java.lang.Exception: Stack trace
at java.lang.Thread.dumpStack(Thread.java:1615)
at anywheresoftware.b4a.shell.Shell.raiseEventImpl(Shell.java:314)
at anywheresoftware.b4a.shell.Shell.raiseEvent(Shell.java:255)
at java.lang.reflect.Method.invoke(Native Method)
at anywheresoftware.b4a.ShellBA.raiseEvent2(ShellBA.java:157)
at anywheresoftware.b4a.BA.raiseEvent(BA.java:201)
at anywheresoftware.b4j.object.JavaObject$1.invoke(JavaObject.java:238)
at java.lang.reflect.Proxy.invoke(Proxy.java:1006)
at $Proxy2.toString(Unknown Source)
at java.lang.String.valueOf(String.java:4102)
at anywheresoftware.b4a.BA.ObjectToString(BA.java:771)
at fr.free.julienGley.RCmotorTester.main._startactivityforresult(main.java:1594)
at fr.free.julienGley.RCmotorTester.main$ResumableSub_SaveAs.resume(main.java:1323)
at fr.free.julienGley.RCmotorTester.main._saveas(main.java:1271)
at fr.free.julienGley.RCmotorTester.main$ResumableSub_Export_click.resume(main.java:1247)
at fr.free.julienGley.RCmotorTester.main._export_click(main.java:1221)
at java.lang.reflect.Method.invoke(Native Method)
at anywheresoftware.b4a.shell.Shell.runMethod(Shell.java:732)
at anywheresoftware.b4a.shell.Shell.raiseEventImpl(Shell.java:348)
at anywheresoftware.b4a.shell.Shell.raiseEvent(Shell.java:255)
at java.lang.reflect.Method.invoke(Native Method)
at anywheresoftware.b4a.ShellBA.raiseEvent2(ShellBA.java:157)
at anywheresoftware.b4a.BA$1.run(BA.java:360)
at android.os.Handler.handleCallback(Handler.java:991)
at android.os.Handler.dispatchMessage(Handler.java:102)
at android.os.Looper.loopOnce(Looper.java:232)
at android.os.Looper.loop(Looper.java:317)
at android.app.ActivityThread.main(ActivityThread.java:8787)
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:591)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:871)
** Activity (main) Pause, UserClosed = false **
 
Upvote 0

freedom2000

Well-Known Member
Licensed User
Longtime User
I found the bug into this post : https://www.b4x.com/android/forum/threads/save-as-to-copy-a-file-is-zero-size.158249/

declaration of "ion" is missing into the snippet of code...

so this code works :

B4X:
Sub SaveAs (Source As InputStream, MimeType As String, Title As String) As ResumableSub
    Dim intent As Intent
    intent.Initialize("android.intent.action.CREATE_DOCUMENT", "")
    intent.AddCategory("android.intent.category.OPENABLE")
    intent.PutExtra("android.intent.extra.TITLE", Title)
    intent.SetType(MimeType)
    StartActivityForResult(intent)
    Wait For ion_Event (MethodName As String, Args() As Object)
    If -1 = Args(0) Then 'resultCode = RESULT_OK
        Dim result As Intent = Args(1)
        Dim jo As JavaObject = result
        Dim ctxt As JavaObject
        Dim ContentResolver As JavaObject = ctxt.InitializeContext.RunMethodJO("getContentResolver", Null)
        Dim out As OutputStream = ContentResolver.RunMethod("openOutputStream", Array(jo.RunMethod("getData", Null), "wt")) 'wt = Write+Trim
        File.Copy2(Source, out)
        out.Close
        Return True
    End If
    Return False
End Sub

Sub StartActivityForResult(i As Intent)
    Dim jo As JavaObject = GetBA
    Private ion As Object
    ion = jo.CreateEvent("anywheresoftware.b4a.IOnActivityResult", "ion", Null)
    jo.RunMethod("startActivityForResult", Array(ion, i))
End Sub

Sub GetBA As Object
    Dim jo As JavaObject
    Dim cls As String = Me
    cls = cls.SubString("class ".Length)
    jo.InitializeStatic(cls)
    Return jo.GetField("processBA")
End Sub
 
Upvote 0
Cookies are required to use this site. You must accept them to continue using the site. Learn more…