Android Question get filesize from ContentChooser

ilan

Expert
Licensed User
Longtime User
hi

i would like to get the filesize from content chooser and if the size if bigger then x i will resize it. how can i do that? i am trying it like this but i always get 0 in logs

B4X:
Sub cr_Result (Success As Boolean, Dir As String, FileName As String)
    Wait For(checkifDirecteryexistsandcreate) Complete (Result As Boolean)
    If Result = False Then Return
        
    Try
        If Success Then
'            Dim targetsize As Long = 300*1024
            
            Log("#######")
            Log(GetPathFromContentResult(FileName))
            Log(File.Size(GetPathFromContentResult(FileName).Replace("/" & FileName,""),FileName))
            
'            Dim ratio As Float = (targetsize / orgsize) * 100
'            If orgsize > targetsize Then
    
'            End If
            
            
            Dim ins As InputStream = File.OpenInput(Dir, FileName)
            Dim bmp As Bitmap
            bmp.Initialize2(ins)
 
            Dim out As OutputStream
            out = File.OpenOutput(File.DirInternal, "userimg.png", False)
            bmp.WriteToStream(out, 100, "JPEG")
            out.Close
    
            
            Log("#######")
            Log(File.Size(File.DirInternal, "userimg.png"))
            
            
            loaduserinfo(False,True) 'load image
        End If       
    Catch
        Log(LastException)
    End Try
End Sub

Sub GetPathFromContentResult(UriString As String) As String
  If UriString.StartsWith("/") Then Return UriString 'If the user used a file manager to choose the image
  Dim Cursor1 As Cursor
  Dim Uri1 As Uri
  Dim Proj() As String = Array As String("_data")
  Dim crs As ContentResolver
  crs.Initialize("")
  If UriString.StartsWith("content://com.android.providers.media.documents") Then
  Dim i As Int = UriString.IndexOf("%3A")
  Dim id As String = UriString.SubString(i + 3)
  Uri1.Parse("content://media/external/images/media")
  Cursor1 = crs.Query(Uri1, Proj, "_id = ?", Array As String(id), "")
  Else
  Uri1.Parse(UriString)
  Cursor1 = crs.Query(Uri1, Proj, "", Null, "")
  End If
  Cursor1.Position = 0
  Dim res As String
  res = Cursor1.GetString("_data")
  Cursor1.Close
  Return res
End Sub

logs:

** Activity (main) Resume **
#######
/storage/3632-3738/DCIM/Camera/20180608_105511.jpg
0
#######
2968068
 

ilan

Expert
Licensed User
Longtime User
There isn't any real file so you cannot check its size. It is a mistake to use GetPathFromContentResult.

If an InputStream is not enough for your requirements then copy it to a temporary file and work with that file.

this is what i was thinking to do, to copy to a temporary file and then delete it but i was thinking maybe there is another way to get the file before do twice the outputstream.

is it possible to get the filesize from inputstream ?? i am trying to avoid saving twice the file. first to get the size and then resize if needed.

thanx, ilan
 
Upvote 0

ilan

Expert
Licensed User
Longtime User
You cannot get the file because there is no file. The data can come from a database, an internal file or any other source.

It is not possible to get the size from the input stream.

thank you very much @Erel, you are awesome!


B4X:
Sub cr_Result (Success As Boolean, Dir As String, FileName As String)
    Wait For(checkifDirecteryexistsandcreate) Complete (Result As Boolean)
    If Result = False Then Return
       
    Try
        If Success Then
            Dim targetsize As Long = 300*1024
            Dim orgsize As Long
            Log("#######")
            Dim ins As InputStream = File.OpenInput(Dir, FileName)
            Dim buffer(targetsize*25) As Byte
            orgsize = ins.ReadBytes(buffer, 0, buffer.length)
            Log(orgsize)
           
            Dim ratio As Float = 100
            If orgsize > targetsize Then ratio = (targetsize / orgsize) * 100

            Dim bmp As Bitmap
            bmp.Initialize2(ins)
 
            Dim out As OutputStream
            out = File.OpenOutput(File.DirInternal, "userimg.png", False)
            bmp.WriteToStream(out, ratio, "JPEG")
            out.Close
            Log("#######")
            Log(File.Size(File.DirInternal, "userimg.png"))
                   
            loaduserinfo(False,True) 'load image
        End If      
    Catch
        Log(LastException)
    End Try
End Sub

** Activity (main) Resume **
#######
2106074
#######
131000
 
Upvote 0

ilan

Expert
Licensed User
Longtime User
btw i found that there is an option to get directly the length of an inputstream without using a byte array

B4X:
fileinputstream.getChannel().size()

can i use javaobject to get the size like that on inputstream?

thank you
 
Upvote 0
Top