From 7f0d509a88f55ced1d0c8fec0d69311d26e4a3a1 Mon Sep 17 00:00:00 2001 From: Matthieu Gautier Date: Thu, 23 Jan 2020 13:25:48 +0100 Subject: [PATCH] Add the filter functionality. --- src/android/filter.cpp | 64 +++++++++++++++++++++ src/android/kiwixreader.cpp | 6 +- src/android/kiwixsearcher.cpp | 2 +- src/android/library.cpp | 5 ++ src/android/meson.build | 3 + src/android/org/kiwix/kiwixlib/Filter.java | 44 ++++++++++++++ src/android/org/kiwix/kiwixlib/Library.java | 2 +- src/android/utils.h | 36 +++++++++++- 8 files changed, 155 insertions(+), 7 deletions(-) create mode 100644 src/android/filter.cpp create mode 100644 src/android/org/kiwix/kiwixlib/Filter.java diff --git a/src/android/filter.cpp b/src/android/filter.cpp new file mode 100644 index 000000000..935b903b0 --- /dev/null +++ b/src/android/filter.cpp @@ -0,0 +1,64 @@ +/* + * Copyright (C) 2019-2020 Matthieu Gautier + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 3 of the License, or + * any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, + * MA 02110-1301, USA. + */ + + +#include +#include +#include "org_kiwix_kiwixlib_Filter.h" + +#include "library.h" +#include "utils.h" + +/* Kiwix Reader JNI functions */ +METHOD0(void, Filter, allocate) { + allocate(env, thisObj); +} + +METHOD0(void, Filter, dispose) { + dispose(env, thisObj); +} + +#define FILTER (getPtr(env, thisObj)) + +#define FORWARD(name, args_type) \ +METHOD(jobject, Filter, name, args_type value) { \ + FILTER->name(jni2c(value, env)); \ + return thisObj; \ +} + +#define FORWARDA(name, args_type) \ +METHOD(jobject, Filter, name, jobjectArray value) { \ + FILTER->name(jni2c(value, env)); \ + return thisObj; \ +} + + + +FORWARD(local, jboolean) +FORWARD(remote, jboolean) +FORWARD(valid, jboolean) +FORWARDA(acceptTags, jstring) +FORWARDA(rejectTags, jstring) +FORWARD(lang, jstring) +FORWARD(publisher, jstring) +FORWARD(creator, jstring) +FORWARD(maxSize, jlong) +FORWARD(query, jstring) + + diff --git a/src/android/kiwixreader.cpp b/src/android/kiwixreader.cpp index 2a4259d53..5b7257d45 100644 --- a/src/android/kiwixreader.cpp +++ b/src/android/kiwixreader.cpp @@ -284,8 +284,8 @@ JNIEXPORT jbyteArray JNICALL Java_org_kiwix_kiwixlib_JNIKiwixReader_getContentPa /* Default values */ /* Retrieve the content */ std::string cUrl = jni2c(url, env); - unsigned int cOffset = jni2c(offset); - unsigned int cLen = jni2c(len); + unsigned int cOffset = jni2c(offset, env); + unsigned int cLen = jni2c(len, env); try { auto entry = READER->getEntryFromEncodedPath(cUrl); entry = entry.getFinalEntry(); @@ -336,7 +336,7 @@ Java_org_kiwix_kiwixlib_JNIKiwixReader_searchSuggestions(JNIEnv* env, { jboolean retVal = JNI_FALSE; std::string cPrefix = jni2c(prefix, env); - unsigned int cCount = jni2c(count); + unsigned int cCount = jni2c(count, env); try { if (READER->searchSuggestionsSmart(cPrefix, cCount)) { diff --git a/src/android/kiwixsearcher.cpp b/src/android/kiwixsearcher.cpp index 1c46836d0..de5f078fa 100644 --- a/src/android/kiwixsearcher.cpp +++ b/src/android/kiwixsearcher.cpp @@ -59,7 +59,7 @@ JNIEXPORT void JNICALL Java_org_kiwix_kiwixlib_JNIKiwixSearcher_search( JNIEnv* env, jobject obj, jstring query, jint count) { std::string cquery = jni2c(query, env); - unsigned int ccount = jni2c(count); + unsigned int ccount = jni2c(count, env); SEARCHER->search(cquery, 0, ccount); } diff --git a/src/android/library.cpp b/src/android/library.cpp index e39fbe308..e10279e22 100644 --- a/src/android/library.cpp +++ b/src/android/library.cpp @@ -79,6 +79,11 @@ METHOD0(jobjectArray, Library, getBooksIds) { return c2jni(LIBRARY->getBooksIds(), env); } +METHOD(jobjectArray, Library, filter, jobject filterObj) { + auto filter = getPtr(env, filterObj); + return c2jni(LIBRARY->filter(*filter), env); +} + METHOD0(jobjectArray, Library, getBooksLanguages) { return c2jni(LIBRARY->getBooksLanguages(), env); } diff --git a/src/android/meson.build b/src/android/meson.build index bb23ab274..dd0889dd1 100644 --- a/src/android/meson.build +++ b/src/android/meson.build @@ -5,6 +5,7 @@ kiwix_jni = custom_target('jni', 'org/kiwix/kiwixlib/JNIKiwixReader.java', 'org/kiwix/kiwixlib/Library.java', 'org/kiwix/kiwixlib/Manager.java', + 'org/kiwix/kiwixlib/Filter.java', 'org/kiwix/kiwixlib/JNIKiwixSearcher.java', 'org/kiwix/kiwixlib/JNIKiwixServer.java', 'org/kiwix/kiwixlib/JNIKiwixInt.java', @@ -17,6 +18,7 @@ kiwix_jni = custom_target('jni', 'org_kiwix_kiwixlib_JNIKiwixReader.h', 'org_kiwix_kiwixlib_Library.h', 'org_kiwix_kiwixlib_Manager.h', + 'org_kiwix_kiwixlib_Filter.h', 'org_kiwix_kiwixlib_JNIKiwixServer.h', 'org_kiwix_kiwixlib_JNIKiwixSearcher.h', 'org_kiwix_kiwixlib_JNIKiwixSearcher_Result.h'], @@ -29,6 +31,7 @@ kiwix_sources += [ 'android/kiwixreader.cpp', 'android/library.cpp', 'android/manager.cpp', + 'android/filter.cpp', 'android/kiwixsearcher.cpp', 'android/kiwixserver.cpp', kiwix_jni] diff --git a/src/android/org/kiwix/kiwixlib/Filter.java b/src/android/org/kiwix/kiwixlib/Filter.java new file mode 100644 index 000000000..bf9e719df --- /dev/null +++ b/src/android/org/kiwix/kiwixlib/Filter.java @@ -0,0 +1,44 @@ +/* + * Copyright (C) 2019-2020 Matthieu Gautier + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 3 of the License, or + * any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, + * MA 02110-1301, USA. + */ + +package org.kiwix.kiwixlib; + +public class Filter +{ + + public native Filter local(boolean accept); + public native Filter remote(boolean accept); + public native Filter valid(boolean accept); + public native Filter acceptTags(String[] tags); + public native Filter rejectTags(String[] tags); + public native Filter lang(String lang); + public native Filter publisher(String publisher); + public native Filter creator(String creator); + public native Filter maxSize(long size); + public native Filter query(String query); + + + public Filter() { allocate(); } + + @Override + protected void finalize() { dispose(); } + private native void allocate(); + private native void dispose(); + private long nativeHandle; +} diff --git a/src/android/org/kiwix/kiwixlib/Library.java b/src/android/org/kiwix/kiwixlib/Library.java index e6776f8d9..68aa7d22f 100644 --- a/src/android/org/kiwix/kiwixlib/Library.java +++ b/src/android/org/kiwix/kiwixlib/Library.java @@ -30,7 +30,7 @@ public class Library public native int getBookCount(boolean localBooks, boolean remoteBooks); public native String[] getBooksIds(); -// public native String[] filter(Filter filter); + public native String[] filter(Filter filter); public native String[] getBooksLanguages(); public native String[] getBooksCreators(); diff --git a/src/android/utils.h b/src/android/utils.h index 289901167..7f51c299e 100644 --- a/src/android/utils.h +++ b/src/android/utils.h @@ -175,9 +175,27 @@ inline jobjectArray c2jni(const std::vector& val, JNIEnv* env) return array; } +template +struct CType { }; + +template<> struct CType{ typedef bool type_t; }; +template<> struct CType{ typedef int type_t; }; +template<> struct CType{ typedef long type_t; }; +template<> struct CType{ typedef std::string type_t; }; + +template +struct CType{ typedef std::vector::type_t> type_t; }; /* jni2c type conversion functions */ -inline bool jni2c(const jboolean& val) { return val == JNI_TRUE; } +template +inline typename CType::type_t jni2c(const T& val, JNIEnv* env) { + return static_cast::type_t>(val); +} + +template<> +inline bool jni2c(const jboolean& val, JNIEnv* env) { return val == JNI_TRUE; } + +template<> inline std::string jni2c(const jstring& val, JNIEnv* env) { const char* chars = env->GetStringUTFChars(val, 0); @@ -186,7 +204,21 @@ inline std::string jni2c(const jstring& val, JNIEnv* env) return ret; } -inline int jni2c(const jint val) { return (int)val; } +template +inline typename CType::type_t jni2c(const jobjectArray& val, JNIEnv* env) +{ + jsize length = env->GetArrayLength(val); + typename CType::type_t v(length); + + int i; + for (i = 0; i < length; i++) { + U obj = (U) env->GetObjectArrayElement(val, i); + auto cobj = jni2c(obj, env); + v.push_back(cobj); + } + return v; +} + /* Method to deal with variable passed by reference */ inline std::string getStringObjValue(const jobject obj, JNIEnv* env) {