translating OpenGL

52 views
Skip to first unread message

Leszek Koltunski

unread,
Apr 12, 2023, 6:03:35 AM4/12/23
to j2objc-discuss
Hello,

I am now researching how to port my Android open source and free app/game ( https://play.google.com/store/apps/details?id=org.distorted.magic ) to iOS.

Obviously it would be perfect if as large as possible part of the code could be auto-translated.

My architecture is as follows:

- at the lowest level, a purely Java and OpenGL layer (you could think of it at a 3D 'game' engine) - 25k LoC. Imports java.* and android.opengl.*
- in the middle, a purely Java library implementing various Rubik-like puzzles - 50k LoC.
  Imports only java.* stuff.
- a small OS 'wrapper' module implementing OS-dependent things like access to local files, logging, etc (500 LoC)
- on top, Android UI (20k LoC)  

The OS-dependent module and the UI I plan to re-implement manually in Swift. The UI layer could (and probably should) be further split into 'really-only-UI' module and 'business logic in pure Java' module to make the number of LoC to be rewritten smaller. The middle layer is hopefully not a problem. 

What is the problem for me is the lowest 'game engine' layer. When I try J2ObjC on it as-is, it complains about android.opengl.* mentions:

./mesh/MeshBase.java:23: error: package android.opengl does not exist
import android.opengl.GLES30;

What are my options here?

1) should I re-write the whole layer in C++ ?
2) maybe it's possible to somehow 'inline' convert only calls to OpenGL to native code?  [sorry, no experience with native  code on Android here so probably I don't know what I am talking about]
3) or maybe it would be possible to 'teach' J2ObjC about OpenGL - after all, as it is platform-independent, translating it should be a relatively simple matter of replacing each 'import android.opengl.GLES30' with whatever #import it should be in Objective-C and changing the function calls slightly?

best,

Leszek

Tom Ball

unread,
Apr 12, 2023, 3:49:21 PM4/12/23
to j2objc-...@googlegroups.com
We don't recommend using j2objc for any UI-related features, especially not for UI-intensive apps like games. In most cases, trying to use j2objc for this is more trouble than it's worth, meaning that you'll spend more time trying to make it work than you'd ever save. 

Have you considered using Flutter instead? A lot of game developers love it, and it has a flutter_gl package which should save you a lot of time and effort. Learning Dart and rewriting your existing app may sound like a big task, but it's likely to be much faster to complete than wrestling with j2objc, and you have a single, cross-platform app source base in the end. j2objc was designed for big, enterprise apps like Gmail and Google Docs (both use it), whereas Flutter is focused on smaller apps with graphics and UI requirements.

--
You received this message because you are subscribed to the Google Groups "j2objc-discuss" group.
To unsubscribe from this group and stop receiving emails from it, send an email to j2objc-discus...@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/j2objc-discuss/87ef31a1-f76f-40ac-8485-6cd5737cb096n%40googlegroups.com.
Message has been deleted

Leszek Koltunski

unread,
Apr 14, 2023, 11:16:04 AM4/14/23
to j2objc-...@googlegroups.com
Hmm... Like I wrote, I plan to re-write the UI layer manually in Swift.
I was hoping 75% of the app - the lower '3D engine' and the middle 'Rubik objects library' could be auto-translated.
And indeed, it seems like we're not far off, J2ObjC is just complaining about the android.opengl imports.

You're saying re-implementing the whole 95k lines of code in Dart would be easier?

You received this message because you are subscribed to a topic in the Google Groups "j2objc-discuss" group.
To unsubscribe from this topic, visit https://groups.google.com/d/topic/j2objc-discuss/3sIs6g8yRqM/unsubscribe.
To unsubscribe from this group and all its topics, send an email to j2objc-discus...@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/j2objc-discuss/CAPLadK7mHDMDZaKXfZCSOBe3Yts0TZ4PyjsuONhf%2BToU_ou72g%40mail.gmail.com.

Leszek Koltunski

unread,
Apr 14, 2023, 11:16:04 AM4/14/23
to j2objc-...@googlegroups.com
It's more of an app than a game, really. Speed is not an issue, we render a single object, 50k-70k triangles (a Rubik-like puzzle).
If only J2ObjC would auto-translate android OpenGL to equivalent iOS OpenGL calls, I'd have 75% of code done...

Tom Ball

unread,
Apr 14, 2023, 11:39:33 AM4/14/23
to j2objc-...@googlegroups.com
The issue with Android's OpenGL library (source code) is that most of its classes have dependencies to Android-specific packages like android.view, android.content, as well as the javax.microedition.khronos.egl packages. Since iOS devices don't have the Android platform built in like Android devices do, every dependency (both direct and indirect) down to the JRE API needs to be built. 

One way to verify this is to try compiling this library's source with javac on the command line, without specifying a -classpath argument. As the javac command fails due to missing package references, then download each of those package's projects from the Android source repository, and add the root source directory to the javac command's -sourcepath, and try again. Unless you get very lucky, you'll soon wind up including most of Android's source code, and still have missing directories. It's just not worth the time and effort.

That's why I recommended something like Flutter, which has an OpenGL library that should work cross-platform. j2objc really only makes sense for a project when you wrote most of the source code that only depends on a few open-source projects, not a big chunk of the Android API.

On Fri, Apr 14, 2023 at 8:16 AM Leszek Koltunski <app.mag...@gmail.com> wrote:
I understand and fully support the decision to stay away from translating UI - i.e. OS-dependent set of widgets. The result never looks quite right on any target.
That's why I plan to re-write the topmost, UI layer, manually in Swift.

But IMHO situation is different with 3D surfaces rendered by OpenGL.OpenGL is supposed to be a fully platform-independent API; translating it should be a relatively simple matter of translating line-by-line, without having to take into account any context - so, each 'import android.opengl.GLES30' would simply be replaced with whatever #import this corresponds to in iOS; same with function calls. Even the function names should be identical.

The end result of the render - the surface being rendered - really should look identically, pixel-by-pixel, on Android and iOS.

And this is what separates me from being about to auto-translate 75K out of 95k lines of code. When I run J2ObjC on the two lower layers - the '3D graphics engine' and the 'Rubik-like objects library' - which together constitute 75k lines out of 95k in total - J2ObjC only complains about the 'android.opengl' imports, nothing else. Which makes me feel like I am very close here... You're saying re-writing the whole 95k lines in Dart would be easier?

Yegor Kurbachev

unread,
Apr 14, 2023, 1:16:16 PM4/14/23
to j2objc-discuss
I actually think that you underestimate how good j2obj2 + gwt combination is.   :)

We have a thin platform specific layer:
— 13k lines in Java for Android
— 12k lines in Java and Objective-C for iOS
— 12k lines in Java and JavaScript for Web
This layer integrates all platform specific external SDKs we use (starting with Google Analytics and Mixpanel and up to Google/Apple/Facebook login and Twilio video conferencing) and includes a translation layer (including right-to-left support), color, font and image abstraction layer and wrappers for GUI components we use.
And the wrappers ensure that components work the exact same way in all platforms, like, for example, they support iOS-style block animations in Android, iOS and Web identically:
  XVL.screen.animate(() -> {
    button.setAlpha(0.5f).setFrame(100f, 0f, 200f, 100f);
    label.setFont(Fonts.BLACK_REGULAR).setBackground(Colors.ITEM_SELECTED);
  });
Android, iOS and Web projects are configured to compile the folders that are relevant to each, thus cross-platform code instantiates com.jvesoft.xvl.Label and gets the platform-correct instance.

The code of the client application itself currently has 418k lines of pure cross-platform Java (including the presentation layer!), which means that over 92% of our code is platform-independent, thanks to you (!!!) and other authors of j2objc and gwt.   :)

Yes, it's been a while since I thanked you for your amazing work!

P.S.: Yes, I had to patch j2objc code to make all anonymous classes have weak reference to their outer classes without a need for an annotation — I have failed to convince you that this is a better way, yet it works so good — literally no memory issues since.   :)

Leszek Koltunski

unread,
Apr 14, 2023, 4:32:47 PM4/14/23
to j2objc-discuss
But why do we even need to include any OpenGL sources in J2ObjC? Wouldn't a static set of 'replacement rules' like so

"import android.opengl.GLES30" --> "#import <OpenGL/OpenGL.h>"   # or whatever it is in iOS

suffice?

Even easier, maybe J2ObjC has some sort of 'ignore the lines between those magic markers' directive? Then I could change my Java code to

/* [ J2ObjC start ignore ] */
import android.opengl.GLES30;
/* [ J2ObjC stop ignore ] */
/* [
#import <OpenGL/OpenGL.h>
] */

And everything would translate to a valid ObjC code?
Reply all
Reply to author
Forward
0 new messages