Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Android support for BigWheels #46

Merged
merged 5 commits into from
Apr 7, 2023
Merged

Conversation

shanminchao
Copy link
Collaborator

@shanminchao shanminchao commented Mar 7, 2023

This is a rough "as-little-change-as-possible" change to enable BigWheels to run on Android. It has been tested with the gbuffer and fishtornado samples successfully (Note: Fishtornado works on Quest2 but fails on Pixel 6. We will have to re-visit fishtornado as a separate task). Among some of the things changed to support Android:

  • Disable imgui
  • Disable cpu_features
  • Abstract file loading so it goes through Android's asset manager (to load assets from APK)
  • Use memory-loading versions of 3rd party libraries (tinyobj, stbi, etc) to avoid using freads
  • Use Android surface and #ifdef out all the glfw code (including input handling)
  • Added all the necessary files to open and build BigWheels from AndroidStudio via Gradle

Todo:

  • Avoid populating root assets folder with build artifacts (i.e. SPV files)
  • Enable cpu_features
  • Enable imgui for Android (not sure if it's practical to do this)
  • Handle inputs
  • Revisit landscape vs portrait orientation and render resolution
  • Find/design some way to run different samples without editing CMakelists
  • Fix fishtornado so that it can run on a Pixel 6

@shanminchao shanminchao force-pushed the android_cleanup branch 6 times, most recently from 5178bdc to 76165d1 Compare March 8, 2023 16:59
Copy link
Contributor

@chaoticbob chaoticbob left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is it necessary to check in all the XML files? Does grade/cmake not generate them during project generation or build time?

# Add game-activity for ANDROID
# ------------------------------------------------------------------------------
if (PPX_ANDROID)
find_package(game-activity REQUIRED CONFIG)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Does this come from the NDK?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yup

@shanminchao
Copy link
Collaborator Author

Is it necessary to check in all the XML files? Does grade/cmake not generate them during project generation or build time?

So the NDK template's .gitignore specifically does not include the specific xml files in the .idea folder that I pushed.
However, in both linux and windows, if I delete the entire .idea folder and re-run Android Studio, those files get
re-generated. So it doesn't seem necessary to push them. I've omitted them in a new commit.

public void useAppContext() {
// Context of the app under test.
Context appContext = InstrumentationRegistry.getInstrumentation().getTargetContext();
assertEquals("com.example.bigwheels", appContext.getPackageName());
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

maybe com.google.bigwheels?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Done


project("bigwheels")

add_subdirectory("../../../../.." "../../../../../app/build")
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Isn't there a variable instead of this .../.../.../.../.../../../../../../ ? like $PPX_DIR or something similar?

Copy link
Collaborator Author

@shanminchao shanminchao Mar 23, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

So no, none of those variables exist. For the Android builds, this CMakeLists.txt file is the first one that cmake encounters, so none of those $PPX_* variables have been setup yet.

I cleaned it up a bit to make it a little more explicit, but it's still ugly relative paths. Not sure what we can do about that. I'm open to suggestions!

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Do any/all of these relative path resolve to similar or the same locations? It might be easier to have a variable that starts a root and then appends the relative paths on. While add_subdirectory implies the current path - it's a little difficult to understand past like 3 relative paths.

Copy link
Collaborator Author

@shanminchao shanminchao Mar 24, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah that's what my cleanup does.

However, Keenuts is working on a subsequent PR that will completely clean up the directory structure and make all this relative path nonsense a thing of the past.

# You can define multiple libraries, and CMake builds them for you.
# Gradle automatically packages shared libraries with your APK.

add_library( # Sets the name of the library.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

file format seems odd? clang-format created those newlines?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks fine to me. What's odd about the file format?

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The new lines between each part of the

add_library\n#comment\n\nbigwheels\n\n#comment\n\nSHARED\n\n#comment\nmaain.cpp

Just unique compared to the other CMakelist.txt

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I see. The cmake was generated by android studio, so I kept it as unmodified as possible. They added newlines so they can add comments, I guess. Do you feel strongly about cleaning it up?

I was following a "as little change as possible to the template" policy in general. But it's not a strict requirement.

android/app/src/main/cpp/main.cpp Show resolved Hide resolved
@@ -0,0 +1,5 @@
<?xml version="1.0" encoding="utf-8"?>
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

All those webp & SVG icons could be replaced by a single xml with like 1 square/shape?

like this one (res/drawable/icon.xml)

<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android" android:shape="rectangle">
  <solid android:color="#FF0000"/>
</shape>

Which ends up looking like so:
6ufVwjKb7AqfASA

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

As discussed offline, Keenuts is working on a subsequent PR that will clean all this nonsense up.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I removed most of the files in the res/ folder, which should reduce the overall size of this PR by about 40KB.

cmake/ShaderCompile.cmake Outdated Show resolved Hide resolved
@@ -30,6 +31,36 @@
# define GLFW_INCLUDE_NONE
#endif
#include <GLFW/glfw3.h>

#if defined(PPX_ANDROID)
#define SETUP_APPLICATION(AppType) \
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Really don't like this part.

What about doing the following:

  • we provide the main function.
  • we have a desktop_main.cc, or android_main.cc, which is compiled depending on the target.
  • this function calls an application_main with argv and the app object.
  • our samples/benchmarks only implements the application_main?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes, that would be a little more involved but definitely cleaner.
In the interest of expediting this PR and getting more people working on Android sooner, I'm going to treat this as a cleanup to be done in a later PR. Ok with you?

pFlockingData->resY = static_cast<int>(mResY);

// For some reason, reading the velocity texture in the vertex shader at the full 128x128 causes a GPU crash on Pixel 6 Pro.
// Also note that when the Pixel Shader is modified to be a solid-color shader, the crash goes away. This even
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Could it be caused by a cross-stage optimization?
if you replace the FS by a solid color, it means you don't read normal/tangent, etc.
So those are dead inputs, meaning VS has dead outputs, so all the instructions generating those can be removed across the whole pipeline, meaning no more texture load?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That doesn't explain why reducing the size makes it automagically work...
In any case, I'm going to leave this as an exercise for someone else to solve. It's enough for the purposes of this PR that fishtornado runs on Android.

Copy link
Collaborator Author

@shanminchao shanminchao Mar 22, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Funnily enough, now fishtornado is broken again even with this fix. I have to disable the flocking shadow pass before it works again. There's definitely something wrong somewhere.

It runs on Quest2 though, although there's minor graphical artifacts.

int value = glfwWindowShouldClose(static_cast<GLFWwindow*>(mWindow));
bool isRunning = (value == 0);
return isRunning;
#else
return true;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

AFAIK this is determined by android_app->destroyRequested.
struct android_app* is provided at the android_main entry.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed

src/ppx/fs.cpp Show resolved Hide resolved
// happens when the FlockingVelocity compute job is disabled and the velocity values are hardcoded to a
// unit vector. Can't make sense of it right now, and it's possible it has to do with SPIR-V code generation,
// since DXC isn't guaranteed to work with mobile.
pFlockingData->resY = 100; //static_cast<int>(mResY);
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

in FlockingRender.hlsl, there is a line in vsmain:

uint2  xy        = uint2((instanceId % Flocking.resX), (instanceId / Flocking.resY));

instanceId is in the range of [0, 128x128-1]

when you make Flocking.resY smaller than 128, the y would be larger than 128 which might cause problems?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ok you're right. Checking in a fix that magically works is probably not a good idea.
I have reverted this hack and made it a TODO to fix fishtornado.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

And I also made the gbuffer sample the default one

@shanminchao shanminchao force-pushed the android_cleanup branch 2 times, most recently from eba66ea to 5303032 Compare April 4, 2023 21:56
Copy link
Member

@Keenuts Keenuts left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

OK for me, except need to propagate the sample fixes to the 3 new samples.


return res;
}
SETUP_APPLICATION(ProjApp)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

3 new samples have been added:

  • 28_gltf
  • oit
  • benchmark fork of 28_gltf

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Added SETUP_APPLICATION to all 3 of these new samples!

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Also added to fluid simulation sample

@Keenuts
Copy link
Member

Keenuts commented Apr 7, 2023

Added a few issues to keep track of the missing work. Assigned some to you, some left for grabs. Feel free to update assignees.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants