Is there a way to import a 3D model into Android? - android

Is it possible to create a simple 3D model (for example in 3DS MAX) and then import it to Android?

That's where I got to:
I've used Google's APIDemos as a starting point - there are rotating cubes in there, each specified by two arrays: vertices and indices.
I've build my model using Blender and exported it as OFF file - it's a text file that lists all the vertices and then faces in terms of these vertices (indexed geometry)
Then I've created a simple C++ app that takes that OFF and writes it as two XMLs containing arrays (one for vertices and one for indices)
These XML files are then copied to res/values and this way I can assign the data they contain to arrays like this:
int vertices[] = context.getResources().getIntArray(R.array.vertices);
I also need to manually change the number of faces to be drawn in here: gl.glDrawElements(GL10.GL_TRIANGLES, 212*6, GL10.GL_UNSIGNED_SHORT, mIndexBuffer); - you can find that number (212 in this case) on top of the OFF file
Here you can find my project page, which uses this solution: Github project > vsiogap3d

you may export it to ASE format.
from ASE, you can convert it to your code manually or programatically.
You will need vertex for vertices array and faces for indices in Android.
don't forget you have to set
gl.glFrontFace(GL10.GL_CCW);
because 3ds max default is counter clockwise.

It should be possible. You can have the file as a data file with your program (and as such it will be pushed onto the emulator and packaged for installation onto an actual device). Then you can write a model loader and viewer in java using the Android and GLES libraries to display the model.
Specific resources on this are probably limited though. 3ds is a proprietry format so 3rd party loaders are in shortish supply and mostly reverse engineered. Other formats (such as blender or milkshape) are more open and you should be able to find details on writing a loader for them in java fairly easily.

Have you tried min3d for android? It supports 3ds max,obj and md2 models.

Not sure about Android specifically, but generally speaking you need a script in 3DS Max that manually writes out the formatting you need from the model.
As to whether one exists for Android or not, I do not know.

You can also convert 3DS MAX model with the 3D Object Converter
http://web.t-online.hu/karpo/
This tool can convert 3ds object to text\xml format or c code.
Please note that the tool is not free. You can try for a 30-day trial period. 'C' code and XML converters are available.
'c' OpenGL output example:
glDisable(GL_TEXTURE_2D);
glEnable(GL_LIGHTING);
glEnable(GL_NORMALIZE);
GLfloat Material_1[] = { 0.498039f, 0.498039f, 0.498039f, 1.000000f };
glBegin(GL_TRIANGLES);
glMaterialfv(GL_FRONT,GL_DIFFUSE,Material_1
glNormal3d(0.452267,0.000000,0.891883);
glVertex3d(5.108326,1.737655,2.650969);
glVertex3d(9.124107,-0.002484,0.614596);
glVertex3d(9.124107,4.039649,0.614596);
glEnd();
Or direct 'c' output:
Point3 Object1_vertex[] = {
{5.108326,1.737655,2.650969},
{9.124107,-0.002484,0.614596},
{9.124107,4.039649,0.614596}};
long Object1_face[] = {
3,0,1,2,
3,3,4,5
3,6,3,5};
You can migrate than those collections of objects to your Java code.

Related

Tensorflow Lite Object Detection with Custom AutoML Model

I like to test the Object Detection Example of TFLite.
https://github.com/tensorflow/examples/tree/master/lite/examples/object_detection/android
The example with the default Model works great. But I want to test a custom Model generated from AutoML. When I am replace the "detect.tflite" and "labelmap fille" in the "\src\main\assets" directory and build then the App crashes after launch.
My Model is very simple ... can detect only 2 objects (Tiger and Lion). And my labelmap file contains below:
???
Tiger
Lion
Also I comment the line "//apply from:'download_model.gradle'" in "build.gradle" to stop the download of default Model and use my custom Model from asset.
I new in both Android and this ML space. I'll be glad if anyone can advise for App crash after launch with custom AutoML Model.
Thanks in advance.
Regards.
Two probable errors on log might be:
Cannot convert between a TensorFlowLite buffer with 1080000 bytes and a ByteBuffer with 270000 bytes. Modify TF_OD_API_INPUT_SIZE accordingly.
tflite ml google [1, 20, 4] and a Java object with shape [1, 10, 4]. Modify NUM_DETECTIONS according to custom model.

Android ArCore Sceneform API. How to change textures in runtime?

The server has more than 3000 models and each of them has several colors of material. I need to load separately models and textures and set textures depending on the user's choice. How to change baseColorMap, normalMap, metallicMap, roughnessMap in runtime?
after
modelRenderable.getMaterial().setTexture("normalMap", normalMap.get());
nothing happens
I'm doing something wrong. There is no information in documentation for that.
thank you for posting this question.
setTexture() appears to not work: Unfortunately this part of our API is still a little rough; it works but is very easy to get wrong. We're working on a sample to illustrate how to modify material parameters (including textures) at runtime and will improve our error reporting in the next release.
Thousands of models w/ multiple permutations how?: The plan here has two parts:
The binaries used by the Android Studio plugin will be made available for use in build scripts on server platforms. This will allow you to do a server-side conversion of your assets to .sfb. We'll be releasing a blog post soon on how to do this.
The .sfa will get the ability to contain loose textures and materials not explicitly associated with geometry, and .sfa's will be able to declare data dependencies on other .sfa's. This will mean that you can author (and deliver) .sfb's that contain textures/materials (but no geometry) and .sfb's that contain geometry (but no textures/materials), and if they're both available at instantiation time it will just work.
use this code`
CompletableFuture<Texture> futureTexture = Texture.builder()
.setSource(this, R.drawable.shoes)
.build();
and replace with
/*.thenAccept(renderable -> andyRenderable = renderable)*/
.thenAcceptBoth(futureTexture, (renderable, texture) -> {
andyRenderable = renderable;
andyRenderable.getMaterial().setTexture("baseColor", texture);
})
would work.

How to customize parameters used on renderscript root function?

Background
I'm new to renderscript, and I would like to try some experiments with it (but small ones and not the complex ones we find in the SDK), so I thought of an exercise to try out, which is based on a previous question of mine (using NDK).
What I want to do
In short, I would like to pass a bitmap data to renderscript, and then I would like it to copy the data to another bitmap that has the dimensions opposite to the previous one, so that the second bitmap would be a rotation of the first one.
For illustration:
From this bitmap (width:2 , height:4):
01
23
45
67
I would like it to rotate (counter clock-wise of 90 degrees) to:
1357
0246
The problem
I've noticed that when I try to change the signature of the root function, Eclipse gives me errors about it.
Even making new functions creates new errors. I've even tried the same code written on Google's blog (here ), but I couldn't find out how he got to create the functions he used, and how come I can't change the filter function to have the input and output bitmap arrays.
What can I do in order to customize the parameters I send to renderscript, and use the data inside it?
Is it ok not to use "filter" or "root" functions (API 11 and above)? What can I do in order to have more flexibility about what I can do there?
You are asking a bunch of separate questions here, so I will answer them in order.
1) You want to rotate a non-square bitmap. Unfortunately, the bitmap model for Renderscript won't allow you to do this easily. The reason for this is that that input and output allocations must have the same shape (i.e. same number of dimensions and values of those dimensions, even if the Types are different). In order to get the effect you want, you should use a root function that only has an output allocation of the new shape (i.e. input columns X input rows). You can create an rs_allocation global variable for holding your input bitmap (which you can then create/bind on the Java side). The kernel then merely needs to set the output cell to the result of rsGetElementAt(globalInAlloc, y, x).
2) If you are using API 11, you can't adjust the signature of the root() function (you can pass NULL allocations as input, output on the Java side if you are not using them). You also can't create more than 1 kernel per source file on these older API levels, so you are forced to only have a single "root()" function. If you want to use more kernels per source file, consider targeting a higher API level.

Get a (Android.Graphics) Path of a String

I cannot find any way to retrieve a Path object representing a string. Does it exist? A list of the necessary points would be enough, but I guess, internally, a path is used.
For example in GDI+ there is:
GraphicsPath p = new GraphicsPath();
p.AddString("string");
From there any point of the "drawn string" can be accessed and modified.
PS: I do not mean drawing a text along a path.
I've spent quite a long time solving this problem (to draw vectorized text in OpenGL) and had to dig deep into libSkia sources. And it turned out pretty simple:
Indeed, canvas uses paths internally and it converts text to vector paths using SkPaint's getTextPath() method. Which is, luckily, exposed at Java side in public API as android.graphics.Paint.getTextPath(). After that, you can read Path back with android.graphics.PathMeasure.
Unfortunately, you can't read exact drawing commands, but you can sample the curve pretty closely using something like bisection.

Complex object in 3d opengl Android

I am given a task of making some complex 3d object in opengl android.Earlier I have worked only on the primitive objects of opengl using nehe tutorials.
I have googled and found that Blender is used to make 3d object and then it is imported in android project .But I cant get HOW?
One easy way to do it is to export your objects in the OBJ format (it describes vertices of an object). You can then easily make your own OBJ reader (or use an existing one) and pass the vertices to OpenGL.
Else, don't reinvent the wheel and use a library that already does this for you (libgdx for instance).
... then it
is imported in android project
Actually it's usually not imported but simply load from file by the target application. There are some export scripts for Blender that emit C code or even write out OpenGL calls; DON'T use them, they'll just mess up your program.
There are some good libraries for 3D object storage, like OpenCTM
What you need is an array of floats that represent your vertices/normals, like so:
float [ ] vertices = {
VertexX, VertexY, VertexZ, NormalX, NormalY, NormalZ,
VertexX, VertexY, VertexZ, NormalX, NormalY, NormalZ,
VertexX, VertexY, VertexZ, NormalX, NormalY, NormalZ,
VertexX, VertexY, VertexZ, NormalX, NormalY, NormalZ,
..., ..., ..., ..., ..., ...,
};
Where each face has three unique vertex lines associated with it. Once you have this array built from an OBJ file or whatever format you want, using code that you'll have to figure out, you can render it by doing the following:
glVertexPointer(3, GL_FLOAT, sizeof(vertices[0])*6, &vertices[0]);
glNormalPoitner(GL_FLOAT, sizeof(vertices[0])*6, &vertices[3]);
glDrawArrays(GL_TRIANGLES, 0, numVertices);
See this Wikipedia page on the OBJ format for reference on how the obj file is laid out. Parsing the file is pretty straightforward once you understand the format.

Categories

Resources