How to display python matplotlib graphs (png) with Chaquopy in Android Studio - android

So I use chaquopy to get simple python programs functioning in an old (jelly bean) tablet (I replace the example console app's main.py in the src directory). Not bad for a beginner's start and I'm very happy.
But now for a test I try to display a matplotlib graph like this:
import matplotlib.pyplot as plt
import matplotlib.image as mpimg
def main():
image = mpimg.imread("/storage/emulated/0/Documents/test.png")
plt.imshow(image)
plt.show()
The matplotlib library was installed from within android studio (albeit with a few missing elements, manual pip3 install and usage of local files). Now the build and program finish without errors, but there is no graph. Installation of pillow and use of other graph types no avail.
Can this be handled in python, or is a dive into android studio / java required?
Thanks for any advice

You'll have to include an ImageView in your app's layout, and then load the image file into it, as in this answer.
For an image which is generated dynamically by matplotlib, either save it to a file and then load from that file, or save it to a bytes object like this:
import io
bio = io.BytesIO()
plt.savefig(bio, format="png")
b = bio.getvalue()
... and then load that bytes object into the ImageView like in this app.

Related

How to read from file using Chaquopy?

I want to read a file using Chaquopy. After some errors like "PermissionError" I wrote the same code in Python Idle and Chaquopy:
This code in Idle writes 'True' in output.
import xlrd, os
filename = 'F:/q1.xlsx'
print(os.path.isfile(filename))
And this one in Chaquopy outputs 'False':
import xlrd, os
filename = 'F:/q1.xlsx'
self.findViewById(R.id.label).setText(str(os.path.isfile(filename)))
I tried all the described combinations of '\' and '/'. It also cannot open a file in the same folder with Python activity if I write only its relative path. How to make Chaquopy work with files correctly?
You can access files either using pkgutil or by using the extractPackages setting. See the documentation for details.

pyqtdeploy: add external modules

is there someone who has experience with pyqtdeploy and adding external modules? I am currently using pyqtdeploy (version 1.2) together with PyQt 5.5.1 to write an application that can be deployed to an Android device. Without any external modules, the freezing with pyqtdeploy works pretty well. However, I am not really sure how I can add external modules (not pure Python ones) to my application.
In particular, I want to add the external module pycrypto. Therefore, I downloaded the pycrypto sourcecode, compiled it with the Android toolchain (from the Android NDK) and now I have a bunch of *.py and *.so files. How can I add them to my application?
My initial attempt was to add the *.py and the *.so files (so basically the whole pycrypto module) to the "Other Packages" tab in pyqtdeploy.
But now, when I import something pycrypto related in my application (from Crypto.Cipher import AES) i get the following error message:
File: ":/Crypto/Cipher/_AES.py", line 20 in __bootstrap__
TypeError: 'NoneType' object is not callable
The _AES.py file where the error is thrown, looks like this:
def __bootstrap__():
global __bootstrap__, __loader__, __file__
import sys, pkgutil, imp
__file__ = pkgutil.get_data(__name__,'_AES.cpython-34m.so')
__loader__ = None; del __bootstrap__, __loader__
imp.load_dynamic(__name__,__file__)
__bootstrap__()
At first I thought, that the *.so filename was just wrong and therefore, I got the NoneType Error, so I changed the filename in _AES.py to something other like 'test.so'. Surprisingly, now, I get a different error message than before:
File ":/pkgutil.py" line 629, in get_data
ImportError: qrcimporter: error opening file :/Crypto/Cipher/test.so
Ok, so the filename should be fine, right? But why do i get the 'NoneType` error message? What am I doing wrong? Is this the right way to accomplish this?
Any help is highly appreciated. I am pretty sure, that i'm only one small step away from getting this thing to work, but I can't figure out what i'm doing wrong.
Thanks!

how do I change directory in ruboto running on android

I'm using ruboto (ruby) on an android tablet. I'd like my source to be in a subdirectory of the usual default source directory. Is there a way to do this?
You have not stated your motivation for placing the Ruby source in a subdirectory, so I'll speculate that it is for tidiness in a polyglot environment. Also, I'll assume you want all the Ruby source in the same directory, including source for Activity classes.
Adding your path to both the Ruby $LOAD_PATH and the Android component search path has been combined into one method in org.ruboto.JRubyAdapter.addLoadPath. In JRubyAdapter.setUpJRuby, you can find a call to addLoadPath around line 289: https://github.com/ruboto/ruboto/blob/1.4.0/assets/src/org/ruboto/JRubyAdapter.java#L289
You can add your own call below the existing one:
addLoadPath("file:" + apkName + "!/<your_path_here>")
That will add the path to the Ruby load path and the Android component search path.
If you have a clear use case, I would submit it to the Ruboto tracker at https://github.com/ruboto/ruboto/issues . It sounds like something more Ruboto developers could use.

Android kivy where to put application files (ini, images db etc)

I've created a prototype application for Android using kivy. It has compiled in buildozer and I've uploaded in to an Android device.
But I'm nor sure where to put app dependent files like the ini file, images database etc.
Any help greatly appreciated
[EDIT 2020 07 25]
When I asked this question (many moons ago) I was new to kivy and the whole idea of buildozer.
What I didn't realise and what isn't obvious to a beginner (witness the number of times this question has been viewed) and which #inclement's answer does not address, is that Buildozer wraps the whole python/kivy project into a single file which can include all of your static data. So you just need to make sure your buildozer spec picks them up.
You can arrange them to taste - as long as you tell buildozer to include them apk (i.e. by setting the file types, directories etc to be included) and access them with relative paths in your code, they will work the same way on the device.
The ini file may be an exception, I'm not sure offhand where kivy tries to load it from (but it may be somewhere in the external data dir). If putting it in the same directory as main.py doesn't work, maybe you could load it manually with a relative path, or if it has just a few values then you could set them in the main.py file.
It worked while I was using the pygame module, I haven't tried it with other modules, but maybe it works.
Folder where buildozer pulls files:
/data/data/package domain.package name /files/app/"
Example
buildozer.spec:
title = application
package.name = myapp
package.domain = org.test
main.py:
import os , sys
import pygame
path = "/data/data/org.test.myapp/files/app"
image = pygame.image.load(path+"image.jpg")
This command line does not work without converting to apk but it works fine when translated
The folder path will only be valid when running on android but... ----->
maybe this will help: ---->
https://youtu.be/XQTIllli6js
and this:
https://github.com/Sahil-pixel/Pygame-for-android/tree/main

Issue with Uncompressing the .7z file in the Android evn

Getting "system.entrypointnotfoundexception: loadlibrary" While trying to use SevenZipLib.dll to uncompress the .7z file containing media contents/file in the Android evn.
Context:
-The whole program is written in c# as a MONO Android Project. No Build/Deployment Error/warnings.
While running the apk, its throwing "system.entrypointnotfoundexception: loadlibrary".
-Also tested the same code as windows project (not mono) - uncompressing in the windows evn.
Assumptions for the issue:
7zip internally might be using COM components & Mono frame work is not supporting.
Question:
Has anyone come across similar issue? Please suggest some alternative dll/framework which can be used by my apk for uncompressing the .7z file.
Assuming that SevenZipLib.dll is the SevenZipLib Library on CodePlex, the problem is SevenZipLib\SevelZipLib\SevenZipArchive.cs:
[DllImport("kernel32.dll", CharSet = CharSet.Auto, SetLastError = true)]
private static extern SafeLibraryHandle LoadLibrary(
[MarshalAs(UnmanagedType.LPTStr)] string lpFileName);
The project contains numerous P/Invokes into kernel32.dll (LoadLibrary(), GetProcAddress(), FreeLibrary()), ole32.dll (PropVariantClear()), oleaut32.dll (SafeArrayCreateVector()), and more.
In short, this library is intimately tied to Windows, and isn't going to work on a non-Windows platform in any meaningful fashion, not without a lot of work.
If you need 7z support in a Mono for Android application, you'll need to look into a different library. It looks like the 7-zip SDK includes C# source for reading LZMA files that doesn't rely on P/Invoke, so perhaps that would work?

Categories

Resources