mirror of
https://gitlab.com/android_translation_layer/android_translation_layer.git
synced 2025-04-28 12:17:57 +03:00
add support for custom Java Drawables
This is made possible, by adding a second Canvas implementation which can be used to render directly to GdkSnapshot objects For now the only implemented method is drawBitmap(), this is already enough to make VectorDrawableCompat functional
This commit is contained in:
parent
0b78cbcc55
commit
ad266c7821
15 changed files with 182 additions and 30 deletions
|
@ -97,6 +97,7 @@ libtranslationlayer_so = shared_library('translation_layer_main', [
|
|||
'src/api-impl-jni/graphics/NinePatchPaintable.c',
|
||||
'src/api-impl-jni/graphics/NinePatchPaintable.c',
|
||||
'src/api-impl-jni/graphics/android_graphics_BitmapFactory.c',
|
||||
'src/api-impl-jni/graphics/android_graphics_GskCanvas.c',
|
||||
'src/api-impl-jni/graphics/android_graphics_Matrix.c',
|
||||
'src/api-impl-jni/graphics/android_graphics_Path.c',
|
||||
'src/api-impl-jni/graphics/android_graphics_Typeface.c',
|
||||
|
|
|
@ -0,0 +1,21 @@
|
|||
/* DO NOT EDIT THIS FILE - it is machine generated */
|
||||
#include <jni.h>
|
||||
/* Header for class android_graphics_GskCanvas */
|
||||
|
||||
#ifndef _Included_android_graphics_GskCanvas
|
||||
#define _Included_android_graphics_GskCanvas
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
/*
|
||||
* Class: android_graphics_GskCanvas
|
||||
* Method: native_drawBitmap
|
||||
* Signature: (JJIIII)V
|
||||
*/
|
||||
JNIEXPORT void JNICALL Java_android_graphics_GskCanvas_native_1drawBitmap
|
||||
(JNIEnv *, jobject, jlong, jlong, jint, jint, jint, jint);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
#endif
|
|
@ -15,6 +15,14 @@ extern "C" {
|
|||
JNIEXPORT jlong JNICALL Java_android_graphics_drawable_Drawable_native_1paintable_1from_1path
|
||||
(JNIEnv *, jclass, jstring);
|
||||
|
||||
/*
|
||||
* Class: android_graphics_drawable_Drawable
|
||||
* Method: native_constructor
|
||||
* Signature: ()J
|
||||
*/
|
||||
JNIEXPORT jlong JNICALL Java_android_graphics_drawable_Drawable_native_1constructor
|
||||
(JNIEnv *, jobject);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
|
16
src/api-impl-jni/graphics/android_graphics_GskCanvas.c
Normal file
16
src/api-impl-jni/graphics/android_graphics_GskCanvas.c
Normal file
|
@ -0,0 +1,16 @@
|
|||
#include <gtk/gtk.h>
|
||||
#include <graphene.h>
|
||||
|
||||
#include "../defines.h"
|
||||
#include "../util.h"
|
||||
|
||||
#include "../generated_headers/android_graphics_GskCanvas.h"
|
||||
|
||||
JNIEXPORT void JNICALL Java_android_graphics_GskCanvas_native_1drawBitmap(JNIEnv *env, jclass this_class, jlong snapshot_ptr, jlong pixbuf_ptr, jint x, jint y, jint width, jint height)
|
||||
{
|
||||
GdkSnapshot *snapshot = (GdkSnapshot *)_PTR(snapshot_ptr);
|
||||
GdkPixbuf *pixbuf = (GdkPixbuf *)_PTR(pixbuf_ptr);
|
||||
GdkTexture *texture = gdk_texture_new_for_pixbuf(pixbuf);
|
||||
gtk_snapshot_append_texture(snapshot, texture, &GRAPHENE_RECT_INIT(x, y, width, height));
|
||||
g_object_unref(texture);
|
||||
}
|
|
@ -2,6 +2,7 @@
|
|||
#include <string.h>
|
||||
|
||||
#include "../defines.h"
|
||||
#include "../util.h"
|
||||
#include "NinePatchPaintable.h"
|
||||
#include "../generated_headers/android_graphics_drawable_Drawable.h"
|
||||
|
||||
|
@ -20,3 +21,49 @@ JNIEXPORT jlong JNICALL Java_android_graphics_drawable_Drawable_native_1paintabl
|
|||
(*env)->ReleaseStringUTFChars(env, pathStr, path);
|
||||
return _INTPTR(paintable);
|
||||
}
|
||||
|
||||
struct _JavaPaintable {
|
||||
GObject parent_instance;
|
||||
jobject drawable;
|
||||
};
|
||||
G_DECLARE_FINAL_TYPE(JavaPaintable, java_paintable, JAVA, PAINTABLE, GObject)
|
||||
|
||||
static void java_paintable_snapshot(GdkPaintable *gdk_paintable, GdkSnapshot *snapshot, double width, double height)
|
||||
{
|
||||
JNIEnv *env = get_jni_env();
|
||||
JavaPaintable *paintable = JAVA_PAINTABLE(gdk_paintable);
|
||||
jclass canvas_class = (*env)->FindClass(env, "android/graphics/GskCanvas");
|
||||
jmethodID canvas_constructor = _METHOD(canvas_class, "<init>", "(J)V");
|
||||
jobject canvas = (*env)->NewObject(env, canvas_class, canvas_constructor, _INTPTR(snapshot));
|
||||
(*env)->CallVoidMethod(env, paintable->drawable, handle_cache.drawable.setBounds, 0, 0, (int)width, (int)height);
|
||||
(*env)->CallVoidMethod(env, paintable->drawable, handle_cache.drawable.draw, canvas);
|
||||
if ((*env)->ExceptionCheck(env))
|
||||
(*env)->ExceptionDescribe(env);
|
||||
(*env)->DeleteLocalRef(env, canvas);
|
||||
(*env)->DeleteLocalRef(env, canvas_class);
|
||||
}
|
||||
|
||||
static void java_paintable_init(JavaPaintable *java_paintable)
|
||||
{
|
||||
}
|
||||
|
||||
static void java_paintable_paintable_init(GdkPaintableInterface *iface)
|
||||
{
|
||||
iface->snapshot = java_paintable_snapshot;
|
||||
}
|
||||
|
||||
static void java_paintable_class_init(JavaPaintableClass *class)
|
||||
{
|
||||
}
|
||||
|
||||
G_DEFINE_TYPE_WITH_CODE(JavaPaintable, java_paintable, G_TYPE_OBJECT,
|
||||
G_IMPLEMENT_INTERFACE(GDK_TYPE_PAINTABLE, java_paintable_paintable_init))
|
||||
|
||||
JNIEXPORT jlong JNICALL Java_android_graphics_drawable_Drawable_native_1constructor(JNIEnv *env, jobject this) {
|
||||
JavaPaintable *paintable = NULL;
|
||||
if (handle_cache.drawable.draw != _METHOD(_CLASS(this), "draw", "(Landroid/graphics/Canvas;)V")) {
|
||||
paintable = g_object_new(java_paintable_get_type(), NULL);
|
||||
paintable->drawable = _REF(this);
|
||||
}
|
||||
return _INTPTR(paintable);
|
||||
}
|
||||
|
|
|
@ -144,6 +144,10 @@ void set_up_handle_cache(JNIEnv *env)
|
|||
|
||||
handle_cache.key_event.class = _REF((*env)->FindClass(env, "android/view/KeyEvent"));
|
||||
handle_cache.key_event.constructor = _METHOD(handle_cache.key_event.class, "<init>", "(II)V");
|
||||
|
||||
handle_cache.drawable.class = _REF((*env)->FindClass(env, "android/graphics/drawable/Drawable"));
|
||||
handle_cache.drawable.draw = _METHOD(handle_cache.drawable.class, "draw", "(Landroid/graphics/Canvas;)V");
|
||||
handle_cache.drawable.setBounds = _METHOD(handle_cache.drawable.class, "setBounds", "(IIII)V");
|
||||
}
|
||||
|
||||
void extract_from_apk(const char *path, const char *target) {
|
||||
|
|
|
@ -100,6 +100,11 @@ struct handle_cache {
|
|||
jclass class;
|
||||
jmethodID constructor;
|
||||
} key_event;
|
||||
struct {
|
||||
jclass class;
|
||||
jmethodID draw;
|
||||
jmethodID setBounds;
|
||||
} drawable;
|
||||
};
|
||||
|
||||
extern struct handle_cache handle_cache;
|
||||
|
|
|
@ -81,7 +81,7 @@ public class Canvas {
|
|||
* @param px The x-coord for the pivot point (unchanged by the rotation)
|
||||
* @param py The y-coord for the pivot point (unchanged by the rotation)
|
||||
*/
|
||||
public final void rotate(float degrees, float px, float py) {
|
||||
public void rotate(float degrees, float px, float py) {
|
||||
native_rotate_and_translate(skia_canvas, widget, degrees, px, py);
|
||||
}
|
||||
// ---
|
||||
|
|
74
src/api-impl/android/graphics/GskCanvas.java
Normal file
74
src/api-impl/android/graphics/GskCanvas.java
Normal file
|
@ -0,0 +1,74 @@
|
|||
package android.graphics;
|
||||
|
||||
/**
|
||||
* GskCanvas:
|
||||
* - implements Canvas for onscreen rendering inside GTKs snapshot function
|
||||
*/
|
||||
public class GskCanvas extends Canvas {
|
||||
private long snapshot;
|
||||
|
||||
public GskCanvas(long snapshot) {
|
||||
System.out.println("GskCanvas(" + snapshot + ")");
|
||||
this.snapshot = snapshot;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int save() {
|
||||
System.out.println("GskCanvas.save()");
|
||||
return -1;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void restore() {
|
||||
System.out.println("GskCanvas.restore()");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void translate(float dx, float dy) {
|
||||
System.out.println("GskCanvas.translate(" + dx + ", " + dy + ")");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void rotate(float degrees) {
|
||||
System.out.println("GskCanvas.rotate(" + degrees + ")");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void drawBitmap(Bitmap bitmap, Rect src, Rect dst, Paint paint) {
|
||||
native_drawBitmap(snapshot, bitmap.pixbuf, dst.left, dst.top, dst.width(), dst.height());
|
||||
}
|
||||
|
||||
@Override
|
||||
public void drawPath(Path path, Paint paint) {
|
||||
System.out.println("GskCanvas.drawPath(" + path + ", " + paint + ")");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void drawRect(float left, float top, float right, float bottom, Paint paint) {
|
||||
System.out.println("GskCanvas.drawRect(" + left + ", " + top + ", " + right + ", " + bottom + ", " + paint + ")");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void rotate(float degrees, float px, float py) {
|
||||
System.out.println("GskCanvas.rotate(" + degrees + ", " + px + ", " + py + ")");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void drawText(String text, float x, float y, Paint paint) {
|
||||
System.out.println("GskCanvas.drawText(" + text + ", " + x + ", " + y + ", " + paint + ")");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void drawLine(float startX, float startY, float stopX, float stopY, Paint paint) {
|
||||
System.out.println("GskCanvas.drawLine(" + startX + ", " + startY + ", " + stopX + ", " + stopY + ", " + paint + ")");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void drawBitmap(Bitmap bitmap, float left, float top, Paint paint) {
|
||||
Rect src = new Rect(0, 0, bitmap.getWidth(), bitmap.getHeight());
|
||||
Rect dst = new Rect((int)left, (int)top, (int)left + bitmap.getWidth(), (int)top + bitmap.getHeight());
|
||||
drawBitmap(bitmap, src, dst, paint);
|
||||
}
|
||||
|
||||
protected native void native_drawBitmap(long snapshot, long pixbuf, int x, int y, int width, int height);
|
||||
}
|
|
@ -28,7 +28,9 @@ public class Drawable {
|
|||
private int[] mStateSet = new int[0];
|
||||
public long paintable;
|
||||
|
||||
public Drawable() {}
|
||||
public Drawable() {
|
||||
this.paintable = native_constructor();
|
||||
}
|
||||
|
||||
public Drawable(long paintable) {
|
||||
this.paintable = paintable;
|
||||
|
@ -180,4 +182,5 @@ public class Drawable {
|
|||
}
|
||||
|
||||
protected static native long native_paintable_from_path(String path);
|
||||
protected native long native_constructor();
|
||||
}
|
||||
|
|
|
@ -1,15 +1,7 @@
|
|||
package android.graphics.drawable;
|
||||
|
||||
import android.graphics.Canvas;
|
||||
|
||||
public class GradientDrawable extends Drawable {
|
||||
|
||||
@Override
|
||||
public void draw(Canvas canvas) {
|
||||
// TODO Auto-generated method stub
|
||||
throw new UnsupportedOperationException("Unimplemented method 'draw'");
|
||||
}
|
||||
|
||||
public void setColor(int color) {}
|
||||
|
||||
public void setCornerRadius(float cornerRadius) {}
|
||||
|
|
|
@ -1,6 +1,5 @@
|
|||
package android.graphics.drawable;
|
||||
|
||||
import android.graphics.Canvas;
|
||||
import android.graphics.Rect;
|
||||
|
||||
public class InsetDrawable extends Drawable {
|
||||
|
@ -9,12 +8,6 @@ public class InsetDrawable extends Drawable {
|
|||
super();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void draw(Canvas canvas) {
|
||||
// TODO Auto-generated method stub
|
||||
throw new UnsupportedOperationException("Unimplemented method 'draw'");
|
||||
}
|
||||
|
||||
public boolean getPadding(Rect padding) { return false; }
|
||||
|
||||
}
|
||||
|
|
|
@ -1,15 +1,9 @@
|
|||
package android.graphics.drawable;
|
||||
|
||||
import android.content.res.ColorStateList;
|
||||
import android.graphics.Canvas;
|
||||
|
||||
public class RippleDrawable extends Drawable {
|
||||
|
||||
public RippleDrawable(ColorStateList colorStateList, Drawable drawable, Drawable drawable2) {}
|
||||
|
||||
@Override
|
||||
public void draw(Canvas canvas) {
|
||||
// TODO Auto-generated method stub
|
||||
throw new UnsupportedOperationException("Unimplemented method 'draw'");
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,6 +1,5 @@
|
|||
package android.graphics.drawable;
|
||||
|
||||
import android.graphics.Canvas;
|
||||
import android.graphics.Paint;
|
||||
import android.graphics.drawable.shapes.Shape;
|
||||
|
||||
|
@ -9,11 +8,5 @@ public class ShapeDrawable extends Drawable {
|
|||
public ShapeDrawable(Shape shape) {}
|
||||
|
||||
public Paint getPaint() {return new Paint();}
|
||||
|
||||
@Override
|
||||
public void draw(Canvas canvas) {
|
||||
// TODO Auto-generated method stub
|
||||
throw new UnsupportedOperationException("Unimplemented method 'draw'");
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -161,6 +161,7 @@ hax_jar = jar('hax', [
|
|||
'android/graphics/Canvas.java',
|
||||
'android/graphics/Color.java',
|
||||
'android/graphics/ColorFilter.java',
|
||||
'android/graphics/GskCanvas.java',
|
||||
'android/graphics/Matrix.java',
|
||||
'android/graphics/Paint.java',
|
||||
'android/graphics/Path.java',
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue