Commit 0e4456b1 authored by Salika Madhushanka W.J's avatar Salika Madhushanka W.J

Merge branch 'master' into 'IT19101620'

Master

See merge request !6
parents c9b5814d 710e9f1b
......@@ -23,7 +23,7 @@ android {
}
python {
buildPython "C:/python/python.exe"
buildPython "D:/Python/python.exe"
pip {
install "opencv-contrib-python-headless"
install "pillow"
......
......@@ -18,11 +18,26 @@
<application
android:allowBackup="true"
android:hardwareAccelerated="false"
android:icon="@drawable/logo"
android:label="@string/app_name"
android:roundIcon="@mipmap/ic_launcher_round"
android:supportsRtl="true"
android:theme="@style/Theme.EKetha">
<activity
android:name=".WeedMain"
android:exported="false">
<meta-data
android:name="android.app.lib_name"
android:value="" />
</activity>
<activity
android:name=".WeedHome"
android:exported="false">
<meta-data
android:name="android.app.lib_name"
android:value="" />
</activity>
<activity
android:name=".PaddyArea.PaddyAreaView_04"
android:exported="false" />
......
......@@ -43,13 +43,13 @@ public class MainActivity extends AppCompatActivity {
// }
// });
//
// cardView2.setOnClickListener(new View.OnClickListener() {
// @Override
// public void onClick(View view) {
// Intent intent = new Intent(getApplicationContext(),weedHome.class);
// startActivity(intent);
// }
// });
cardView2.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
Intent intent = new Intent(getApplicationContext(),WeedHome.class);
startActivity(intent);
}
});
//
cardView3.setOnClickListener(new View.OnClickListener() {
@Override
......
package com.example.eketha;
import androidx.appcompat.app.AppCompatActivity;
import android.content.Intent;
import android.os.Bundle;
import android.view.View;
import android.widget.LinearLayout;
import android.widget.Toast;
public class WeedHome extends AppCompatActivity {
private LinearLayout layer1, layer2;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_weed_home);
layer1 = findViewById(R.id.layer2);
layer2 = findViewById(R.id.layer3);
layer1.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
Intent intent = new Intent(getApplicationContext(),WeedMain.class);
startActivity(intent);
}
});
layer2.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
Intent launchIntent = getPackageManager().getLaunchIntentForPackage("org.tensorflow.lite.examples.imagesegmentation");
if (launchIntent != null) {
startActivity(launchIntent);
} else {
Toast.makeText(getApplicationContext(), "There is no package available in android", Toast.LENGTH_LONG).show();
}
}
});
}
}
\ No newline at end of file
package com.example.eketha;
import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.annotation.RequiresApi;
import androidx.appcompat.app.AppCompatActivity;;
import com.example.eketha.ml.Modelres;
import android.Manifest;
import android.content.Intent;
import android.content.pm.PackageManager;
import android.graphics.Bitmap;
import android.media.ThumbnailUtils;
import android.net.Uri;
import android.os.Build;
import android.os.Bundle;
import android.provider.MediaStore;
import android.view.View;
import android.widget.Button;
import android.widget.ImageView;
import android.widget.TextView;
import org.tensorflow.lite.DataType;
import org.tensorflow.lite.support.label.Category;
import org.tensorflow.lite.support.tensorbuffer.TensorBuffer;
import java.io.IOException;
import java.nio.ByteBuffer;
import java.nio.ByteOrder;
import java.util.Comparator;
import java.util.List;
public class WeedMain extends AppCompatActivity {
Button camera, gallery;
ImageView imageView;
TextView result;
int imageSize = 224;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_weed_main);
camera = findViewById(R.id.btnTakePictureWeed);
gallery = findViewById(R.id.btnLaunchGalleryweed);
result = findViewById(R.id.classifiedWeed);
imageView = findViewById(R.id.imageViewWeed);
camera.setOnClickListener(new View.OnClickListener() {
@RequiresApi(api = Build.VERSION_CODES.M)
@Override
public void onClick(View view) {
if (checkSelfPermission(Manifest.permission.CAMERA) == PackageManager.PERMISSION_GRANTED) {
Intent cameraIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
startActivityForResult(cameraIntent, 3);
} else {
requestPermissions(new String[]{Manifest.permission.CAMERA}, 100);
}
}
});
gallery.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
Intent cameraIntent = new Intent(Intent.ACTION_PICK, MediaStore.Images.Media.EXTERNAL_CONTENT_URI);
startActivityForResult(cameraIntent, 1);
}
});
}
@RequiresApi(api = Build.VERSION_CODES.N)
@Override
protected void onActivityResult(int requestCode, int resultCode, @Nullable Intent data) {
if(resultCode == RESULT_OK){
if(requestCode == 3){
Bitmap image = (Bitmap) data.getExtras().get("data");
int dimension = Math.min(image.getWidth(), image.getHeight());
image = ThumbnailUtils.extractThumbnail(image, dimension, dimension);
imageView.setImageBitmap(image);
image = Bitmap.createScaledBitmap(image, imageSize, imageSize, false);
classifyImage(image);
}else{
Uri dat = data.getData();
Bitmap image = null;
try {
image = MediaStore.Images.Media.getBitmap(this.getContentResolver(), dat);
} catch (IOException e) {
e.printStackTrace();
}
imageView.setImageBitmap(image);
image = Bitmap.createScaledBitmap(image, imageSize, imageSize, false);
classifyImage(image);
}
}
super.onActivityResult(requestCode, resultCode, data);
}
@RequiresApi(api = Build.VERSION_CODES.N)
public void classifyImage(Bitmap image){
try {
Modelres model = Modelres.newInstance(getApplicationContext());
// Creates inputs for reference.
TensorBuffer inputFeature0 = TensorBuffer.createFixedSize(new int[]{1, 224, 224, 3}, DataType.UINT8);
ByteBuffer byteBuffer = ByteBuffer.allocateDirect(1 * imageSize * imageSize * 3);
byteBuffer.order(ByteOrder.nativeOrder());
int[] intValues = new int[imageSize * imageSize];
image.getPixels(intValues, 0, image.getWidth(), 0, 0, image.getWidth(), image.getHeight());
int pixel = 0;
//iterate over each pixel and extract R, G, and B values. Add those values individually to the byte buffer.
for(int i = 0; i < imageSize; i ++){
for(int j = 0; j < imageSize; j++){
int val = intValues[pixel++]; // RGB
byteBuffer.put((byte) (((val >> 16) & 0xFF) * (1.f / 1)));
byteBuffer.put((byte) (((val >> 8) & 0xFF) * (1.f / 1)));
byteBuffer.put((byte) ((val & 0xFF) * (1.f / 1)));
}
}
inputFeature0.loadBuffer(byteBuffer);
// Runs model inference and gets result.
Modelres.Outputs outputs = model.process(inputFeature0);
List<Category> probability = outputs.getProbabilityAsCategoryList();
//TensorBuffer outputFeature0 = (TensorBuffer) outputs.getProbabilityAsCategoryList();
// find the index of the class with the biggest confidence.
// int maxPos = 0;
// float maxConfidence = 0;
// for (int i = 0; i < probability.size(); i++) {
// if (probability.get(i) > maxConfidence) {
// maxConfidence = probability[i];
// maxPos = i;
// }
// }
// String[] classes = {"unlabeled", "weed", "rice","sand"};
// result.setText(classes[maxPos]);
probability.sort(Comparator.comparing(Category::getScore, Comparator.reverseOrder()));
for (int i=0; i<3; i++)
result.setText( probability.get(i).getLabel() +" : " + probability.get(i).getScore());
// Releases model resources if no longer used.
model.close();
} catch (IOException e) {
// TODO Handle the exception
}
}
}
\ No newline at end of file
# Image Segmentation Android sample.
The used model, DeepLab
[https://ai.googleblog.com/2018/03/semantic-image-segmentation-with.html] is a
state-of-art deep learning model for semantic image segmentation, where the goal
is to assign semantic labels (e.g. person, dog, cat) to every pixel in the input
image.
## Requirements
* Android Studio 3.2 (installed on a Linux, Mac or Windows machine)
* An Android device, or an Android Emulator
## Build and run
### Step 1. Clone the TensorFlow examples source code
Clone the TensorFlow examples GitHub repository to your computer to get the demo
application.
```
git clone https://github.com/tensorflow/examples
```
### Step 2. Import the sample app to Android Studio
Open the TensorFlow source code in Android Studio. To do this, open Android
Studio and select `Import Projects (Gradle, Eclipse ADT, etc.)`, setting the
folder to `examples/lite/examples/image_segmentation/android`
### Step 3. Run the Android app
Connect the Android device to the computer and be sure to approve any ADB
permission prompts that appear on your phone. Select `Run -> Run app.` Select
the deployment target in the connected devices to the device on which the app
will be installed. This will install the app on the device.
To test the app, open the app called `TFL Image Segmentation` on your device.
Re-installing the app may require you to uninstall the previous installations.
## Resources used:
* Camera2:
https://developer.android.com/reference/android/hardware/camera2/package-summary
* Camera2 base sample:
https://github.com/android/camera-samples/tree/master/Camera2Formats
* TensorFlow Lite: https://www.tensorflow.org/lite
* ImageSegmentation model:
https://www.tensorflow.org/lite/models/segmentation/overview
# Image Segmentation Android sample.
The used model, DeepLab [https://ai.googleblog.com/2018/03/semantic-image-segmentation-with.html]
is a state-of-art deep learning model for semantic image segmentation,
where the goal is to assign semantic labels (e.g. person, dog, cat) to every pixel in the input
image.
## Requirements
* Android Studio 3.2 (installed on a Linux, Mac or Windows machine)
* An Android device, or an Android Emulator
## Build and run
### Step 1. Clone the TensorFlow examples source code
Clone the TensorFlow examples GitHub repository to your computer to get the
demo application.
```
git clone https://github.com/tensorflow/examples
```
### Step 2. Import the sample app to Android Studio
Open the TensorFlow source code in Android Studio. To do this, open Android
Studio and select `Import Projects (Gradle, Eclipse ADT, etc.)`, setting the
folder to `examples/lite/examples/image_segmentation/android`
### Step 3. Run the Android app
Connect the Android device to the computer and be sure to approve any ADB
permission prompts that appear on your phone. Select `Run -> Run app.` Select
the deployment target in the connected devices to the device on which the app
will be installed. This will install the app on the device.
To test the app, open the app called `TFL Image Segmentation` on your device.
Re-installing the app may require you to uninstall the previous installations.
## Resources used:
* Camera2: https://developer.android.com/reference/android/hardware/camera2/package-summary
* Canera2 base sample: https://github.com/android/camera-samples/tree/master/Camera2Formats
* TensorFlow Lite: https://www.tensorflow.org/lite
* ImageSegmentation model: https://www.tensorflow.org/lite/models/segmentation/overview
\ No newline at end of file
package com.example.eketha.WeedSegmentation.android.app
apply plugin: 'com.android.application'
apply plugin: 'kotlin-android'
apply plugin: 'kotlin-android-extensions'
android {
compileSdkVersion 29
buildToolsVersion "29.0.2"
defaultConfig {
applicationId "org.tensorflow.lite.examples.imagesegmentation"
minSdkVersion 21
targetSdkVersion 29
versionCode 1
versionName "1.0"
testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner"
}
buildTypes {
release {
minifyEnabled false
proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro'
}
}
aaptOptions {
noCompress "tflite"
}
compileOptions {
sourceCompatibility JavaVersion.VERSION_1_8
targetCompatibility JavaVersion.VERSION_1_8
}
// If you find lint problem like:
// * What went wrong:
// A problem was found with the configuration of task ':app:lint'.
// > No value has been specified for property 'lintClassPath'.
//
// Probably you haven't set ANDROID_HOME. To fix:
// export ANDROID_HOME=$HOME/Android/Sdk # Your Android SDK path.
lintOptions {
abortOnError false
}
flavorDimensions "tfliteInference"
productFlavors {
// The TFLite inference is built using the TFLite Java API.
interpreter {
dimension "tfliteInference"
}
// The TFLite inference is built using the TFLite Task library.
taskApi {
dimension "tfliteInference"
}
}
}
// App assets folder:
project.ext.ASSET_DIR = projectDir.toString() + '/src/main/assets'
// Download TF Lite model.
apply from: 'download.gradle'
dependencies {
implementation fileTree(dir: 'libs', include: ['*.jar'])
interpreterImplementation project(":lib_interpreter")
taskApiImplementation project(":lib_task_api")
implementation project(":lib_utils")
implementation 'androidx.appcompat:appcompat:1.1.0'
implementation 'androidx.constraintlayout:constraintlayout:1.1.3'
implementation 'androidx.coordinatorlayout:coordinatorlayout:1.1.0'
implementation 'androidx.legacy:legacy-support-v4:1.0.0'
implementation 'androidx.lifecycle:lifecycle-extensions:2.2.0'
implementation 'androidx.lifecycle:lifecycle-viewmodel:2.2.0'
implementation 'androidx.recyclerview:recyclerview:1.1.0'
implementation 'com.github.bumptech.glide:glide:4.11.0'
implementation 'com.google.android.material:material:1.1.0'
implementation 'com.google.code.gson:gson:2.8.6'
implementation 'com.google.guava:guava:28.2-android'
implementation 'org.jetbrains.kotlin:kotlin-stdlib:1.3.71'
implementation 'org.jetbrains.kotlinx:kotlinx-coroutines-android:1.3.0'
implementation 'org.jetbrains.kotlinx:kotlinx-coroutines-core:1.3.0'
}
package com.example.eketha.WeedSegmentation.android.app
apply plugin: 'de.undercouch.download'
task downloadModelFile(type: Download) {
src 'https://drive.google.com/uc?export=download&id=1QJDizlgnJk_9V6uwM5hM-NOEpdc_Lz9g'
dest project.ext.ASSET_DIR + '/deeplabv3_257_mv_gpu.tflite'
overwrite true
}
preBuild.dependsOn downloadModelFile
\ No newline at end of file
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="org.tensorflow.lite.examples.imagesegmentation">
</manifest>
/*
* Copyright 2019 The TensorFlow Authors. All Rights Reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.example.eketha.WeedSegmentation.android.app.src.androidTest.java.org.tensorflow.lite.examples.imagesegmentation;
import static com.google.common.truth.Truth.assertThat;
import android.content.Context;
import android.content.res.AssetManager;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.util.Log;
import androidx.test.ext.junit.runners.AndroidJUnit4;
import androidx.test.platform.app.InstrumentationRegistry;
import java.io.IOException;
import java.io.InputStream;
import java.util.Collections;
import java.util.HashSet;
import java.util.Set;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.tensorflow.lite.examples.imagesegmentation.tflite.ImageSegmentationModelExecutor;
import org.tensorflow.lite.examples.imagesegmentation.tflite.ModelExecutionResult;
/** Golden test for Image Segmentation Reference app. */
@RunWith(AndroidJUnit4.class)
public class ImageSegmentationModelExecutorTest {
private static final String INPUT = "input_image.jpg";
private static final String GOLDEN_OUTPUTS_TASK = "golden_output_task.png";
private static final double GOLDEN_MASK_TOLERANCE = 1e-2;
private static final String[] goldenLabelArray = {"background", "person", "horse"};
@Test
public void executeResultsShouldNotChange() throws IOException {
Context context = InstrumentationRegistry.getInstrumentation().getContext();
ImageSegmentationModelExecutor segmenter = new ImageSegmentationModelExecutor(context, false);
Bitmap input = loadImage(INPUT);
ModelExecutionResult result = segmenter.execute(input);
// Verify the output mask bitmap.
if (ImageSegmentationModelExecutor.TAG.equals("SegmentationTask")) {
String goldenOutputFileName = GOLDEN_OUTPUTS_TASK;
int[] goldenPixels = getPixels(loadImage(goldenOutputFileName));
int[] resultPixels = getPixels(result.getBitmapMaskOnly());
assertThat(resultPixels).hasLength(goldenPixels.length);
int inconsistentPixels = 0;
for (int i = 0; i < resultPixels.length; i++) {
if (resultPixels[i] != goldenPixels[i]) {
inconsistentPixels++;
}
}
assertThat((double) inconsistentPixels / resultPixels.length)
.isLessThan(GOLDEN_MASK_TOLERANCE);
}
// Verify labels.
Set<String> resultLabels = new HashSet<>();
for (String itemName : result.getItemsFound().keySet()) {
resultLabels.add(itemName);
}
Set<String> goldenLabels = new HashSet<>();
Collections.addAll(goldenLabels, goldenLabelArray);
assertThat(resultLabels).isEqualTo(goldenLabels);
}
private static int[] getPixels(Bitmap bitmap) {
int width = bitmap.getWidth();
int height = bitmap.getHeight();
int[] pixels = new int[width * height];
bitmap.getPixels(pixels, 0, width, 0, 0, width, height);
return pixels;
}
private static Bitmap loadImage(String fileName) {
AssetManager assetManager =
InstrumentationRegistry.getInstrumentation().getContext().getAssets();
InputStream inputStream = null;
try {
inputStream = assetManager.open(fileName);
} catch (IOException e) {
Log.e("Test", "Cannot load image from assets");
}
return BitmapFactory.decodeStream(inputStream);
}
}
<?xml version="1.0" encoding="utf-8"?>
<!--
Copyright 2019 The TensorFlow Authors. All Rights Reserved.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
package="org.tensorflow.lite.examples.imagesegmentation">
<!-- Do not remove, it is needed for internal build system -->
<uses-sdk />
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
<uses-permission android:name="android.permission.CAMERA" />
<uses-feature android:name="android.hardware.camera.any" />
<application
android:allowBackup="true"
android:icon="@drawable/logo"
android:label="E-Ketha Segmentation"
android:roundIcon="@drawable/logo"
android:supportsRtl="true"
android:theme="@style/AppTheme.ImageSegmentation"
android:requestLegacyExternalStorage="true"
tools:ignore="GoogleAppIndexingWarning">
<activity
android:name=".MainActivity"
android:screenOrientation="portrait"
android:exported="true">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
</application>
</manifest>
/*
* Copyright 2019 Google LLC
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* https://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.tensorflow.lite.examples.imagesegmentation
import androidx.lifecycle.LiveData
import androidx.lifecycle.MutableLiveData
import androidx.lifecycle.ViewModel
import android.util.Log
import java.io.File
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.ExecutorCoroutineDispatcher
import kotlinx.coroutines.Job
import kotlinx.coroutines.launch
import org.tensorflow.lite.examples.imagesegmentation.tflite.ImageSegmentationModelExecutor
import org.tensorflow.lite.examples.imagesegmentation.tflite.ModelExecutionResult
import org.tensorflow.lite.examples.imagesegmentation.utils.ImageUtils
private const val TAG = "MLExecutionViewModel"
class MLExecutionViewModel : ViewModel() {
private val _resultingBitmap = MutableLiveData<ModelExecutionResult>()
val resultingBitmap: LiveData<ModelExecutionResult>
get() = _resultingBitmap
private val viewModelJob = Job()
private val viewModelScope = CoroutineScope(viewModelJob)
// the execution of the model has to be on the same thread where the interpreter
// was created
fun onApplyModel(
filePath: String,
imageSegmentationModel: ImageSegmentationModelExecutor?,
inferenceThread: ExecutorCoroutineDispatcher
) {
viewModelScope.launch(inferenceThread) {
val contentImage =
ImageUtils.decodeBitmap(
File(filePath)
)
try {
val result = imageSegmentationModel?.execute(contentImage)
_resultingBitmap.postValue(result)
} catch (e: Exception) {
Log.e(TAG, "Fail to execute ImageSegmentationModelExecutor: ${e.message}")
_resultingBitmap.postValue(null)
}
}
}
}
/*
* Copyright 2019 Google LLC
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* https://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.tensorflow.lite.examples.imagesegmentation.camera
import android.content.Context
import android.util.AttributeSet
import android.util.Log
import android.view.SurfaceView
import kotlin.math.roundToInt
/**
* A [SurfaceView] that can be adjusted to a specified aspect ratio and
* performs center-crop transformation of input frames.
*/
class AutoFitSurfaceView(
context: Context,
attrs: AttributeSet? = null,
defStyle: Int = 0
) : SurfaceView(context, attrs, defStyle) {
private var aspectRatio = 0f
private var widthDiff = 0
private var heightDiff = 0
private var requestLayout = false
/**
* Sets the aspect ratio for this view. The size of the view will be
* measured based on the ratio calculated from the parameters. Note that
* the actual sizes of parameters don't matter, that is, calling
* setAspectRatio(2, 3) and setAspectRatio(4, 6) make the same result.
*
* @param width Relative horizontal size
* @param height Relative vertical size
*/
fun setAspectRatio(width: Int, height: Int) {
require(width > 0 && height > 0) { "Size cannot be negative" }
aspectRatio = width.toFloat() / height.toFloat()
requestLayout()
}
override fun onMeasure(widthMeasureSpec: Int, heightMeasureSpec: Int) {
val width = MeasureSpec.getSize(widthMeasureSpec)
val height = MeasureSpec.getSize(heightMeasureSpec)
if (aspectRatio == 0f) {
setMeasuredDimension(width, height)
} else {
// Performs center-crop transformation of the camera frames
val newWidth: Int
val newHeight: Int
if (width < height * aspectRatio) {
newHeight = height
newWidth = (height / aspectRatio).roundToInt()
} else {
newWidth = width
newHeight = (width / aspectRatio).roundToInt()
}
Log.d(TAG, "Measured dimensions set: $newWidth x $newHeight")
widthDiff = width - newWidth
heightDiff = height - newHeight
requestLayout = true
setMeasuredDimension(newWidth, newHeight)
}
}
override fun onLayout(changed: Boolean, left: Int, top: Int, right: Int, bottom: Int) {
if (requestLayout) {
requestLayout = false
layout(
widthDiff / 2,
heightDiff / 2,
right + (widthDiff / 2),
bottom + (heightDiff / 2)
)
}
super.onLayout(changed, left, top, right, bottom)
}
companion object {
private val TAG = AutoFitSurfaceView::class.java.simpleName
}
}
/*
* Copyright 2019 Google LLC
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* https://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.tensorflow.lite.examples.imagesegmentation.camera
import android.graphics.Point
import android.hardware.camera2.CameraCharacteristics
import android.hardware.camera2.params.StreamConfigurationMap
import android.util.Size
import android.view.Display
import kotlin.math.max
import kotlin.math.min
/** Helper class used to pre-compute shortest and longest sides of a [Size] */
class SmartSize(width: Int, height: Int) {
var size = Size(width, height)
var long = max(size.width, size.height)
var short = min(size.width, size.height)
override fun toString() = "SmartSize(${long}x$short)"
}
/** Standard High Definition size for pictures and video */
val SIZE_1080P: SmartSize = SmartSize(1920, 1080)
/** Returns a [SmartSize] object for the given [Display] */
fun getDisplaySmartSize(display: Display): SmartSize {
val outPoint = Point()
display.getRealSize(outPoint)
return SmartSize(outPoint.x, outPoint.y)
}
// verify that the given width and height are on the expected aspect ratio
fun verifyAspectRatio(width: Int, height: Int, aspectRatio: Size): Boolean {
return (width * aspectRatio.height) == (height * aspectRatio.width)
}
/**
* Returns the largest available PREVIEW size. For more information, see:
* https://d.android.com/reference/android/hardware/camera2/CameraDevice
*/
fun <T> getPreviewOutputSize(
display: Display,
characteristics: CameraCharacteristics,
targetClass: Class<T>,
aspectRatio: Size,
format: Int? = null
): Size {
// Find which is smaller: screen or 1080p
val screenSize = getDisplaySmartSize(display)
val hdScreen = screenSize.long >= SIZE_1080P.long || screenSize.short >= SIZE_1080P.short
val maxSize = if (hdScreen) SIZE_1080P else screenSize
// If image format is provided, use it to determine supported sizes; else use target class
val config = characteristics.get(
CameraCharacteristics.SCALER_STREAM_CONFIGURATION_MAP
)!!
if (format == null) {
assert(StreamConfigurationMap.isOutputSupportedFor(targetClass))
} else {
assert(config.isOutputSupportedFor(format))
}
val allSizes = if (format == null) {
config.getOutputSizes(targetClass)
} else {
config.getOutputSizes(format)
}
// Get available sizes and sort them by area from largest to smallest
val validSizes = allSizes
.sortedWith(compareBy { it.height * it.width })
.filter { verifyAspectRatio(it.width, it.height, aspectRatio) }
.map { SmartSize(it.width, it.height) }.reversed()
// Then, get the largest output size that is smaller or equal than our max size
return validSizes.first { it.long <= maxSize.long && it.short <= maxSize.short }.size
}
/*
* Copyright 2019 Google LLC
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* https://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.tensorflow.lite.examples.imagesegmentation.camera
import androidx.lifecycle.LiveData
import android.content.Context
import android.hardware.camera2.CameraCharacteristics
import android.view.OrientationEventListener
import android.view.Surface
/**
* Calculates closest 90-degree orientation to compensate for the device
* rotation relative to sensor orientation, i.e., allows user to see camera
* frames with the expected orientation.
*/
class OrientationLiveData(
context: Context,
characteristics: CameraCharacteristics
) : LiveData<Int>() {
private val listener = object : OrientationEventListener(context.applicationContext) {
override fun onOrientationChanged(orientation: Int) {
val rotation = when {
orientation <= 45 -> Surface.ROTATION_0
orientation <= 135 -> Surface.ROTATION_90
orientation <= 225 -> Surface.ROTATION_180
orientation <= 315 -> Surface.ROTATION_270
else -> Surface.ROTATION_0
}
val relative = computeRelativeRotation(characteristics, rotation)
if (relative != value) postValue(relative)
}
}
override fun onActive() {
super.onActive()
listener.enable()
}
override fun onInactive() {
super.onInactive()
listener.disable()
}
companion object {
/**
* Computes rotation required to transform from the camera sensor orientation to the
* device's current orientation in degrees.
*
* @param characteristics the [CameraCharacteristics] to query for the sensor orientation.
* @param surfaceRotation the current device orientation as a Surface constant
* @return the relative rotation from the camera sensor to the current device orientation.
*/
@JvmStatic
private fun computeRelativeRotation(
characteristics: CameraCharacteristics,
surfaceRotation: Int
): Int {
val sensorOrientationDegrees =
characteristics.get(CameraCharacteristics.SENSOR_ORIENTATION)!!
val deviceOrientationDegrees = when (surfaceRotation) {
Surface.ROTATION_0 -> 0
Surface.ROTATION_90 -> 90
Surface.ROTATION_180 -> 180
Surface.ROTATION_270 -> 270
else -> 0
}
// Reverse device orientation for front-facing cameras
val sign = if (characteristics.get(CameraCharacteristics.LENS_FACING) ==
CameraCharacteristics.LENS_FACING_FRONT
) 1 else -1
// Calculate desired JPEG orientation relative to camera orientation to make
// the image upright relative to the device orientation
return (sensorOrientationDegrees - (deviceOrientationDegrees * sign) + 360) % 360
}
}
}
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android" >
<scale
android:duration="1500"
android:fromXScale="0.85"
android:toXScale="1.0"
android:fromYScale="0.85"
android:toYScale="1.0"
android:pivotX="50%"
android:pivotY="50%"
android:repeatCount="infinite"
android:repeatMode="reverse"/>
</set>
\ No newline at end of file
<vector xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:aapt="http://schemas.android.com/aapt"
android:width="108dp"
android:height="108dp"
android:viewportHeight="108"
android:viewportWidth="108">
<path
android:fillType="evenOdd"
android:pathData="M32,64C32,64 38.39,52.99 44.13,50.95C51.37,48.37 70.14,49.57 70.14,49.57L108.26,87.69L108,109.01L75.97,107.97L32,64Z"
android:strokeColor="#00000000"
android:strokeWidth="1">
<aapt:attr name="android:fillColor">
<gradient
android:endX="78.5885"
android:endY="90.9159"
android:startX="48.7653"
android:startY="61.0927"
android:type="linear">
<item
android:color="#44000000"
android:offset="0.0"/>
<item
android:color="#00000000"
android:offset="1.0"/>
</gradient>
</aapt:attr>
</path>
<path
android:fillColor="#FFFFFF"
android:fillType="nonZero"
android:pathData="M66.94,46.02L66.94,46.02C72.44,50.07 76,56.61 76,64L32,64C32,56.61 35.56,50.11 40.98,46.06L36.18,41.19C35.45,40.45 35.45,39.3 36.18,38.56C36.91,37.81 38.05,37.81 38.78,38.56L44.25,44.05C47.18,42.57 50.48,41.71 54,41.71C57.48,41.71 60.78,42.57 63.68,44.05L69.11,38.56C69.84,37.81 70.98,37.81 71.71,38.56C72.44,39.3 72.44,40.45 71.71,41.19L66.94,46.02ZM62.94,56.92C64.08,56.92 65,56.01 65,54.88C65,53.76 64.08,52.85 62.94,52.85C61.8,52.85 60.88,53.76 60.88,54.88C60.88,56.01 61.8,56.92 62.94,56.92ZM45.06,56.92C46.2,56.92 47.13,56.01 47.13,54.88C47.13,53.76 46.2,52.85 45.06,52.85C43.92,52.85 43,53.76 43,54.88C43,56.01 43.92,56.92 45.06,56.92Z"
android:strokeColor="#00000000"
android:strokeWidth="1"/>
</vector>
<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
android:shape="rectangle">
<corners
android:topLeftRadius="@dimen/tfe_bottom_sheet_corner_radius"
android:topRightRadius="@dimen/tfe_bottom_sheet_corner_radius" />
<padding android:top="@dimen/tfe_bottom_sheet_top_padding" />
<solid android:color="@android:color/white" />
</shape>
\ No newline at end of file
<?xml version="1.0" encoding="utf-8"?>
<vector xmlns:android="http://schemas.android.com/apk/res/android"
android:width="108dp"
android:height="108dp"
android:viewportHeight="108"
android:viewportWidth="108">
<path
android:fillColor="#26A69A"
android:pathData="M0,0h108v108h-108z" />
<path
android:fillColor="#00000000"
android:pathData="M9,0L9,108"
android:strokeColor="#33FFFFFF"
android:strokeWidth="0.8" />
<path
android:fillColor="#00000000"
android:pathData="M19,0L19,108"
android:strokeColor="#33FFFFFF"
android:strokeWidth="0.8" />
<path
android:fillColor="#00000000"
android:pathData="M29,0L29,108"
android:strokeColor="#33FFFFFF"
android:strokeWidth="0.8" />
<path
android:fillColor="#00000000"
android:pathData="M39,0L39,108"
android:strokeColor="#33FFFFFF"
android:strokeWidth="0.8" />
<path
android:fillColor="#00000000"
android:pathData="M49,0L49,108"
android:strokeColor="#33FFFFFF"
android:strokeWidth="0.8" />
<path
android:fillColor="#00000000"
android:pathData="M59,0L59,108"
android:strokeColor="#33FFFFFF"
android:strokeWidth="0.8" />
<path
android:fillColor="#00000000"
android:pathData="M69,0L69,108"
android:strokeColor="#33FFFFFF"
android:strokeWidth="0.8" />
<path
android:fillColor="#00000000"
android:pathData="M79,0L79,108"
android:strokeColor="#33FFFFFF"
android:strokeWidth="0.8" />
<path
android:fillColor="#00000000"
android:pathData="M89,0L89,108"
android:strokeColor="#33FFFFFF"
android:strokeWidth="0.8" />
<path
android:fillColor="#00000000"
android:pathData="M99,0L99,108"
android:strokeColor="#33FFFFFF"
android:strokeWidth="0.8" />
<path
android:fillColor="#00000000"
android:pathData="M0,9L108,9"
android:strokeColor="#33FFFFFF"
android:strokeWidth="0.8" />
<path
android:fillColor="#00000000"
android:pathData="M0,19L108,19"
android:strokeColor="#33FFFFFF"
android:strokeWidth="0.8" />
<path
android:fillColor="#00000000"
android:pathData="M0,29L108,29"
android:strokeColor="#33FFFFFF"
android:strokeWidth="0.8" />
<path
android:fillColor="#00000000"
android:pathData="M0,39L108,39"
android:strokeColor="#33FFFFFF"
android:strokeWidth="0.8" />
<path
android:fillColor="#00000000"
android:pathData="M0,49L108,49"
android:strokeColor="#33FFFFFF"
android:strokeWidth="0.8" />
<path
android:fillColor="#00000000"
android:pathData="M0,59L108,59"
android:strokeColor="#33FFFFFF"
android:strokeWidth="0.8" />
<path
android:fillColor="#00000000"
android:pathData="M0,69L108,69"
android:strokeColor="#33FFFFFF"
android:strokeWidth="0.8" />
<path
android:fillColor="#00000000"
android:pathData="M0,79L108,79"
android:strokeColor="#33FFFFFF"
android:strokeWidth="0.8" />
<path
android:fillColor="#00000000"
android:pathData="M0,89L108,89"
android:strokeColor="#33FFFFFF"
android:strokeWidth="0.8" />
<path
android:fillColor="#00000000"
android:pathData="M0,99L108,99"
android:strokeColor="#33FFFFFF"
android:strokeWidth="0.8" />
<path
android:fillColor="#00000000"
android:pathData="M19,29L89,29"
android:strokeColor="#33FFFFFF"
android:strokeWidth="0.8" />
<path
android:fillColor="#00000000"
android:pathData="M19,39L89,39"
android:strokeColor="#33FFFFFF"
android:strokeWidth="0.8" />
<path
android:fillColor="#00000000"
android:pathData="M19,49L89,49"
android:strokeColor="#33FFFFFF"
android:strokeWidth="0.8" />
<path
android:fillColor="#00000000"
android:pathData="M19,59L89,59"
android:strokeColor="#33FFFFFF"
android:strokeWidth="0.8" />
<path
android:fillColor="#00000000"
android:pathData="M19,69L89,69"
android:strokeColor="#33FFFFFF"
android:strokeWidth="0.8" />
<path
android:fillColor="#00000000"
android:pathData="M19,79L89,79"
android:strokeColor="#33FFFFFF"
android:strokeWidth="0.8" />
<path
android:fillColor="#00000000"
android:pathData="M29,19L29,89"
android:strokeColor="#33FFFFFF"
android:strokeWidth="0.8" />
<path
android:fillColor="#00000000"
android:pathData="M39,19L39,89"
android:strokeColor="#33FFFFFF"
android:strokeWidth="0.8" />
<path
android:fillColor="#00000000"
android:pathData="M49,19L49,89"
android:strokeColor="#33FFFFFF"
android:strokeWidth="0.8" />
<path
android:fillColor="#00000000"
android:pathData="M59,19L59,89"
android:strokeColor="#33FFFFFF"
android:strokeWidth="0.8" />
<path
android:fillColor="#00000000"
android:pathData="M69,19L69,89"
android:strokeColor="#33FFFFFF"
android:strokeWidth="0.8" />
<path
android:fillColor="#00000000"
android:pathData="M79,19L79,89"
android:strokeColor="#33FFFFFF"
android:strokeWidth="0.8" />
</vector>
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<item android:state_pressed="true">
<shape android:shape="oval">
<stroke android:width="4dp" android:color="#66EEEEEE" />
<size android:height="64dp" android:width="64dp" />
</shape>
</item>
<item android:state_focused="true">
<shape android:shape="oval">
<stroke android:width="4dp" android:color="#AAEEEEEE" />
<size android:height="64dp" android:width="64dp" />
</shape>
</item>
<item>
<shape android:shape="oval">
<stroke android:width="4dp" android:color="#DDEEEEEE" />
<size android:height="64dp" android:width="64dp" />
</shape>
</item>
</selector>
\ No newline at end of file
<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
android:shape="rectangle">
<solid
android:color="@color/tfe_is_color_light_gray">
</solid>
<stroke
android:width="0dp"
android:color="#424242">
</stroke>
<corners
android:topLeftRadius="30dp"
android:topRightRadius="30dp"
android:bottomLeftRadius="0dp"
android:bottomRightRadius="0dp">
</corners>
</shape>
<?xml version="1.0" encoding="utf-8"?>
<androidx.coordinatorlayout.widget.CoordinatorLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="#00000000"
tools:context="org.tensorflow.lite.examples.imagesegmentation.MainActivity">
<androidx.appcompat.widget.Toolbar
android:id="@+id/toolbar"
android:layout_width="match_parent"
android:layout_height="?attr/actionBarSize"
android:background="@android:color/white"/>
<LinearLayout
android:id="@+id/images_container"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical"
android:gravity="center_horizontal"
android:paddingTop="?attr/actionBarSize">
<LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:gravity="center_horizontal">
<LinearLayout
android:id="@+id/layer1"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:orientation="vertical">
<ImageView
android:layout_width="150dp"
android:layout_height="150dp"
android:layout_marginLeft="100dp"
android:layout_marginTop="30dp"
app:srcCompat="@drawable/logo" />
<TextView
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:text="Weed Segmentation"
android:textColor="@color/design_default_color_primary_dark"
android:layout_marginTop="10dp"
android:layout_marginLeft="40dp"
android:textSize="30dp"/>
</LinearLayout>
<FrameLayout
android:id="@+id/view_finder"
android:layout_width="30dp"
android:layout_height="30dp"
android:paddingTop="16dp"
android:visibility="invisible" />
</LinearLayout>
<HorizontalScrollView
android:layout_width="match_parent"
android:layout_height="wrap_content">
<LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:orientation="horizontal">
<ImageView
android:id="@+id/original_imageview"
android:layout_width="@dimen/tfe_is_preview_size"
android:layout_height="@dimen/tfe_is_preview_size"
android:padding="8dp" />
<ImageView
android:id="@+id/result_imageview"
android:layout_width="@dimen/tfe_is_preview_size"
android:layout_height="@dimen/tfe_is_preview_size"
android:padding="8dp" />
<ImageView
android:id="@+id/mask_imageview"
android:layout_width="@dimen/tfe_is_preview_size"
android:layout_height="@dimen/tfe_is_preview_size"
android:padding="8dp" />
</LinearLayout>
</HorizontalScrollView>
</LinearLayout>
<include
layout="@layout/tfe_is_bottom_sheet_layout"
android:visibility="invisible" />
<com.google.android.material.floatingactionbutton.FloatingActionButton
android:id="@+id/capture_button"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_margin="16dp"
android:layout_marginEnd="8dp"
android:clickable="true"
app:backgroundTint="@android:color/white"
app:layout_anchor="@id/bottom_sheet"
app:layout_anchorGravity="top|end"
app:srcCompat="@android:drawable/ic_menu_camera" />
<View
android:id="@+id/dummy"
android:layout_width="1dp"
android:layout_height="80dp"
android:layout_marginEnd="8dp"
app:layout_anchor="@id/capture_button"
app:layout_anchorGravity="top|right|end" />
<com.google.android.material.floatingactionbutton.FloatingActionButton
android:id="@+id/toggle_button"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_margin="16dp"
android:layout_marginEnd="8dp"
android:clickable="true"
app:backgroundTint="@android:color/white"
app:layout_anchor="@id/dummy"
app:layout_anchorGravity="top|end"
app:srcCompat="@android:drawable/ic_popup_sync" />
</androidx.coordinatorlayout.widget.CoordinatorLayout>
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/bottom_sheet"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_margin="8dp"
android:background="@drawable/rounded_edge"
android:orientation="vertical"
android:paddingTop="10dp"
android:paddingBottom="16dp"
app:behavior_hideable="false"
app:behavior_peekHeight="36dp"
app:layout_behavior="com.google.android.material.bottomsheet.BottomSheetBehavior"
tools:showIn="@layout/tfe_is_activity_main">
<ImageView
android:id="@+id/bottom_sheet_arrow"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:src="@drawable/icn_chevron_up" />
<Switch
android:id="@+id/switch_use_gpu"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginStart="8dp"
android:layout_marginEnd="8dp"
android:text="@string/tfe_is_gpu" />
<TextView
android:id="@+id/log_view"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:textAppearance="@style/TextAppearance.AppCompat.Medium"
android:padding="8dp"
android:layout_marginStart="8dp"
android:layout_marginEnd="8dp"
android:textColor="@android:color/black" />
<TextView
android:id="@+id/tfe_is_labels_found"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="8dp"
android:layout_marginStart="8dp"
android:layout_marginEnd="8dp"
android:text="@string/tfe_is_labels_found" />
<com.google.android.material.chip.ChipGroup
android:id="@+id/chips_group"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_margin="16dp"
app:chipSpacingVertical="4dp" />
<Button
android:id="@+id/rerun_button"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:padding="8dp"
android:text="@string/tfe_is_re_run_model" />
</LinearLayout>
<?xml version="1.0" encoding="utf-8"?>
<adaptive-icon xmlns:android="http://schemas.android.com/apk/res/android">
<background android:drawable="@android:color/white"/>
<foreground android:drawable="@mipmap/ic_launcher_foreground"/>
</adaptive-icon>
<?xml version="1.0" encoding="utf-8"?>
<adaptive-icon xmlns:android="http://schemas.android.com/apk/res/android">
<background android:drawable="@android:color/white"/>
<foreground android:drawable="@mipmap/ic_launcher_foreground"/>
</adaptive-icon>
<?xml version="1.0" encoding="utf-8"?>
<resources>
<color name="tfe_color_primary">#34D80E</color>
<color name="tfe_color_primary_dark">#0D6703</color>
<color name="tfe_color_accent">#425066</color>
<color name="tfe_is_color_light_gray">#E4E4E4</color>
</resources>
<?xml version="1.0" encoding="utf-8"?>
<resources>
<dimen name="tfe_is_preview_size">300dp</dimen>
<dimen name="tfe_bottom_sheet_corner_radius">15dp</dimen>
<dimen name="tfe_bottom_sheet_top_padding">8dp</dimen>
</resources>
\ No newline at end of file
<resources>
<string name="tfe_is_app_name" translatable="false">TFL Image Segmentation</string>
<string name="tfe_is_gpu" translatable="false">GPU</string>
<string name="tfe_is_re_run_model" translatable="false">Re-run model</string>
<string name="tfe_is_labels_found" translatable="false">Labels Found</string>
<string name="tfe_is_no_labels_found" translatable="false">No Labels Found</string>
</resources>
<resources>
<!-- Base application theme. -->
<style name="AppTheme.ImageSegmentation" parent="Theme.MaterialComponents.Light.NoActionBar">
<!-- Customize your theme here. -->
<item name="colorPrimary">@color/tfe_color_primary</item>
<item name="colorPrimaryDark">@color/tfe_color_primary_dark</item>
<item name="colorAccent">@color/tfe_color_accent</item>
</style>
</resources>
package com.example.eketha.WeedSegmentation.android
// Top-level build file where you can add configuration options common to all sub-projects/modules.
buildscript {
repositories {
google()
jcenter()
}
dependencies {
classpath 'com.android.tools.build:gradle:4.0.0'
classpath 'de.undercouch:gradle-download-task:4.0.2'
classpath 'org.jetbrains.kotlin:kotlin-gradle-plugin:1.3.71'
// NOTE: Do not place your application dependencies here; they belong
// in the individual module build.gradle files
}
}
allprojects {
repositories {
google()
jcenter()
}
}
task clean(type: Delete) {
delete rootProject.buildDir
}
# Project-wide Gradle settings.
# IDE (e.g. Android Studio) users:
# Gradle settings configured through the IDE *will override*
# any settings specified in this file.
# For more details on how to configure your build environment visit
# http://www.gradle.org/docs/current/userguide/build_environment.html
# Specifies the JVM arguments used for the daemon process.
# The setting is particularly useful for tweaking memory settings.
org.gradle.jvmargs=-Xmx1536m
# When configured, Gradle will run in incubating parallel mode.
# This option should only be used with decoupled projects. More details, visit
# http://www.gradle.org/docs/current/userguide/multi_project_builds.html#sec:decoupled_projects
# org.gradle.parallel=true
# AndroidX package structure to make it clearer which packages are bundled with the
# Android operating system, and which are packaged with your app's APK
# https://developer.android.com/topic/libraries/support-library/androidx-rn
android.useAndroidX=true
# Automatically convert third-party libraries to use AndroidX
android.enableJetifier=true
distributionBase=GRADLE_USER_HOME
distributionPath=wrapper/dists
distributionUrl=https\://services.gradle.org/distributions/gradle-6.1.1-bin.zip
zipStoreBase=GRADLE_USER_HOME
zipStorePath=wrapper/dists
#!/usr/bin/env sh
#
# Copyright 2015 the original author or authors.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# https://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
#
##############################################################################
##
## Gradle start up script for UN*X
##
##############################################################################
# Attempt to set APP_HOME
# Resolve links: $0 may be a link
PRG="$0"
# Need this for relative symlinks.
while [ -h "$PRG" ] ; do
ls=`ls -ld "$PRG"`
link=`expr "$ls" : '.*-> \(.*\)$'`
if expr "$link" : '/.*' > /dev/null; then
PRG="$link"
else
PRG=`dirname "$PRG"`"/$link"
fi
done
SAVED="`pwd`"
cd "`dirname \"$PRG\"`/" >/dev/null
APP_HOME="`pwd -P`"
cd "$SAVED" >/dev/null
APP_NAME="Gradle"
APP_BASE_NAME=`basename "$0"`
# Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
DEFAULT_JVM_OPTS='"-Xmx64m" "-Xms64m"'
# Use the maximum available, or set MAX_FD != -1 to use that value.
MAX_FD="maximum"
warn () {
echo "$*"
}
die () {
echo
echo "$*"
echo
exit 1
}
# OS specific support (must be 'true' or 'false').
cygwin=false
msys=false
darwin=false
nonstop=false
case "`uname`" in
CYGWIN* )
cygwin=true
;;
Darwin* )
darwin=true
;;
MINGW* )
msys=true
;;
NONSTOP* )
nonstop=true
;;
esac
CLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar
# Determine the Java command to use to start the JVM.
if [ -n "$JAVA_HOME" ] ; then
if [ -x "$JAVA_HOME/jre/sh/java" ] ; then
# IBM's JDK on AIX uses strange locations for the executables
JAVACMD="$JAVA_HOME/jre/sh/java"
else
JAVACMD="$JAVA_HOME/bin/java"
fi
if [ ! -x "$JAVACMD" ] ; then
die "ERROR: JAVA_HOME is set to an invalid directory: $JAVA_HOME
Please set the JAVA_HOME variable in your environment to match the
location of your Java installation."
fi
else
JAVACMD="java"
which java >/dev/null 2>&1 || die "ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.
Please set the JAVA_HOME variable in your environment to match the
location of your Java installation."
fi
# Increase the maximum file descriptors if we can.
if [ "$cygwin" = "false" -a "$darwin" = "false" -a "$nonstop" = "false" ] ; then
MAX_FD_LIMIT=`ulimit -H -n`
if [ $? -eq 0 ] ; then
if [ "$MAX_FD" = "maximum" -o "$MAX_FD" = "max" ] ; then
MAX_FD="$MAX_FD_LIMIT"
fi
ulimit -n $MAX_FD
if [ $? -ne 0 ] ; then
warn "Could not set maximum file descriptor limit: $MAX_FD"
fi
else
warn "Could not query maximum file descriptor limit: $MAX_FD_LIMIT"
fi
fi
# For Darwin, add options to specify how the application appears in the dock
if $darwin; then
GRADLE_OPTS="$GRADLE_OPTS \"-Xdock:name=$APP_NAME\" \"-Xdock:icon=$APP_HOME/media/gradle.icns\""
fi
# For Cygwin or MSYS, switch paths to Windows format before running java
if [ "$cygwin" = "true" -o "$msys" = "true" ] ; then
APP_HOME=`cygpath --path --mixed "$APP_HOME"`
CLASSPATH=`cygpath --path --mixed "$CLASSPATH"`
JAVACMD=`cygpath --unix "$JAVACMD"`
# We build the pattern for arguments to be converted via cygpath
ROOTDIRSRAW=`find -L / -maxdepth 1 -mindepth 1 -type d 2>/dev/null`
SEP=""
for dir in $ROOTDIRSRAW ; do
ROOTDIRS="$ROOTDIRS$SEP$dir"
SEP="|"
done
OURCYGPATTERN="(^($ROOTDIRS))"
# Add a user-defined pattern to the cygpath arguments
if [ "$GRADLE_CYGPATTERN" != "" ] ; then
OURCYGPATTERN="$OURCYGPATTERN|($GRADLE_CYGPATTERN)"
fi
# Now convert the arguments - kludge to limit ourselves to /bin/sh
i=0
for arg in "$@" ; do
CHECK=`echo "$arg"|egrep -c "$OURCYGPATTERN" -`
CHECK2=`echo "$arg"|egrep -c "^-"` ### Determine if an option
if [ $CHECK -ne 0 ] && [ $CHECK2 -eq 0 ] ; then ### Added a condition
eval `echo args$i`=`cygpath --path --ignore --mixed "$arg"`
else
eval `echo args$i`="\"$arg\""
fi
i=`expr $i + 1`
done
case $i in
0) set -- ;;
1) set -- "$args0" ;;
2) set -- "$args0" "$args1" ;;
3) set -- "$args0" "$args1" "$args2" ;;
4) set -- "$args0" "$args1" "$args2" "$args3" ;;
5) set -- "$args0" "$args1" "$args2" "$args3" "$args4" ;;
6) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" ;;
7) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" ;;
8) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" ;;
9) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" "$args8" ;;
esac
fi
# Escape application args
save () {
for i do printf %s\\n "$i" | sed "s/'/'\\\\''/g;1s/^/'/;\$s/\$/' \\\\/" ; done
echo " "
}
APP_ARGS=`save "$@"`
# Collect all arguments for the java command, following the shell quoting and substitution rules
eval set -- $DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS "\"-Dorg.gradle.appname=$APP_BASE_NAME\"" -classpath "\"$CLASSPATH\"" org.gradle.wrapper.GradleWrapperMain "$APP_ARGS"
exec "$JAVACMD" "$@"
@rem
@rem Copyright 2015 the original author or authors.
@rem
@rem Licensed under the Apache License, Version 2.0 (the "License");
@rem you may not use this file except in compliance with the License.
@rem You may obtain a copy of the License at
@rem
@rem https://www.apache.org/licenses/LICENSE-2.0
@rem
@rem Unless required by applicable law or agreed to in writing, software
@rem distributed under the License is distributed on an "AS IS" BASIS,
@rem WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
@rem See the License for the specific language governing permissions and
@rem limitations under the License.
@rem
@if "%DEBUG%" == "" @echo off
@rem ##########################################################################
@rem
@rem Gradle startup script for Windows
@rem
@rem ##########################################################################
@rem Set local scope for the variables with windows NT shell
if "%OS%"=="Windows_NT" setlocal
set DIRNAME=%~dp0
if "%DIRNAME%" == "" set DIRNAME=.
set APP_BASE_NAME=%~n0
set APP_HOME=%DIRNAME%
@rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
set DEFAULT_JVM_OPTS="-Xmx64m" "-Xms64m"
@rem Find java.exe
if defined JAVA_HOME goto findJavaFromJavaHome
set JAVA_EXE=java.exe
%JAVA_EXE% -version >NUL 2>&1
if "%ERRORLEVEL%" == "0" goto init
echo.
echo ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.
echo.
echo Please set the JAVA_HOME variable in your environment to match the
echo location of your Java installation.
goto fail
:findJavaFromJavaHome
set JAVA_HOME=%JAVA_HOME:"=%
set JAVA_EXE=%JAVA_HOME%/bin/java.exe
if exist "%JAVA_EXE%" goto init
echo.
echo ERROR: JAVA_HOME is set to an invalid directory: %JAVA_HOME%
echo.
echo Please set the JAVA_HOME variable in your environment to match the
echo location of your Java installation.
goto fail
:init
@rem Get command-line arguments, handling Windows variants
if not "%OS%" == "Windows_NT" goto win9xME_args
:win9xME_args
@rem Slurp the command line arguments.
set CMD_LINE_ARGS=
set _SKIP=2
:win9xME_args_slurp
if "x%~1" == "x" goto execute
set CMD_LINE_ARGS=%*
:execute
@rem Setup the command line
set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar
@rem Execute Gradle
"%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %CMD_LINE_ARGS%
:end
@rem End local scope for the variables with windows NT shell
if "%ERRORLEVEL%"=="0" goto mainEnd
:fail
rem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of
rem the _cmd.exe /c_ return code!
if not "" == "%GRADLE_EXIT_CONSOLE%" exit 1
exit /b 1
:mainEnd
if "%OS%"=="Windows_NT" endlocal
:omega
package com.example.eketha.WeedSegmentation.android.lib_interpreter
apply plugin: 'com.android.library'
apply plugin: 'kotlin-android'
apply plugin: 'kotlin-android-extensions'
android {
compileSdkVersion 29
buildToolsVersion "29.0.0"
defaultConfig {
minSdkVersion 21
targetSdkVersion 29
versionCode 1
versionName "1.0"
testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner"
}
buildTypes {
release {
minifyEnabled false
proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro'
}
}
aaptOptions {
noCompress "tflite"
}
// If you find lint problem like:
// * What went wrong:
// A problem was found with the configuration of task ':app:lint'.
// > No value has been specified for property 'lintClassPath'.
//
// Probably you haven't set ANDROID_HOME. To fix:
// export ANDROID_HOME=$HOME/Android/Sdk # Your Android SDK path.
lintOptions {
abortOnError false
}
}
dependencies {
implementation fileTree(dir: 'libs', include: ['*.jar'])
implementation project(":lib_utils")
implementation 'androidx.appcompat:appcompat:1.1.0'
implementation 'org.jetbrains.kotlin:kotlin-stdlib:1.3.71'
implementation('org.tensorflow:tensorflow-lite:0.0.0-nightly') { changing = true }
implementation('org.tensorflow:tensorflow-lite-gpu:0.0.0-nightly') { changing = true }
}
/**
* Automatically generated file. DO NOT MODIFY
*/
package com.example.eketha.WeedSegmentation.android.lib_interpreter.build.generated.source.buildConfig.debug.org.tensorflow.lite.examples.imagesegmentation.tflite;
public final class BuildConfig {
public static final boolean DEBUG = Boolean.parseBoolean("true");
public static final String LIBRARY_PACKAGE_NAME = "org.tensorflow.lite.examples.imagesegmentation.tflite";
public static final String BUILD_TYPE = "debug";
public static final int VERSION_CODE = 1;
public static final String VERSION_NAME = "1.0";
}
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="org.tensorflow.lite.examples.imagesegmentation.tflite"
android:versionCode="1"
android:versionName="1.0" > <!-- Do not remove, it is needed for internal build system -->
<uses-sdk
android:minSdkVersion="21"
android:targetSdkVersion="29" />
</manifest>
\ No newline at end of file
{
"version": 1,
"applicationId": "org.tensorflow.lite.examples.imagesegmentation.tflite",
"variantType": "LIBRARY",
"elements": [
{
"outputType": {
"type": "AAPT_FRIENDLY_MERGED_MANIFESTS"
},
"apkData": {
"type": "MAIN",
"splits": [],
"versionCode": 1,
"versionName": "1.0",
"outputFile": "lib_interpreter-debug.aar",
"fullName": "debug",
"baseName": "debug",
"dirName": ""
},
"path": "AndroidManifest.xml",
"properties": {
"packageId": "org.tensorflow.lite.examples.imagesegmentation.tflite",
"split": ""
}
}
]
}
\ No newline at end of file
<?xml version="1.0" encoding="utf-8"?>
<merger version="3"><dataSet config="main" ignore_pattern="!.svn:!.git:!.ds_store:!*.scc:.*:&lt;dir>_*:!CVS:!thumbs.db:!picasa.ini:!*~"><source path="D:\Research\android\lib_interpreter\src\main\jniLibs"/></dataSet><dataSet config="debug" ignore_pattern="!.svn:!.git:!.ds_store:!*.scc:.*:&lt;dir>_*:!CVS:!thumbs.db:!picasa.ini:!*~"><source path="D:\Research\android\lib_interpreter\src\debug\jniLibs"/></dataSet></merger>
\ No newline at end of file
<?xml version="1.0" encoding="utf-8"?>
<merger version="3"><dataSet config="main" ignore_pattern="!.svn:!.git:!.ds_store:!*.scc:.*:&lt;dir>_*:!CVS:!thumbs.db:!picasa.ini:!*~"><source path="D:\Research\android\lib_interpreter\src\main\shaders"/></dataSet><dataSet config="debug" ignore_pattern="!.svn:!.git:!.ds_store:!*.scc:.*:&lt;dir>_*:!CVS:!thumbs.db:!picasa.ini:!*~"><source path="D:\Research\android\lib_interpreter\src\debug\shaders"/></dataSet></merger>
\ No newline at end of file
<?xml version="1.0" encoding="utf-8"?>
<merger version="3"><dataSet config="main" ignore_pattern="!.svn:!.git:!.ds_store:!*.scc:.*:&lt;dir>_*:!CVS:!thumbs.db:!picasa.ini:!*~"><source path="D:\Research\android\lib_interpreter\src\main\assets"/><source path="D:\Research\android\lib_interpreter\build\intermediates\shader_assets\debug\out"/></dataSet><dataSet config="debug" ignore_pattern="!.svn:!.git:!.ds_store:!*.scc:.*:&lt;dir>_*:!CVS:!thumbs.db:!picasa.ini:!*~"><source path="D:\Research\android\lib_interpreter\src\debug\assets"/></dataSet></merger>
\ No newline at end of file
<?xml version="1.0" encoding="utf-8"?>
<merger version="3"><dataSet aapt-namespace="http://schemas.android.com/apk/res-auto" config="main$Generated" generated="true" ignore_pattern="!.svn:!.git:!.ds_store:!*.scc:.*:&lt;dir>_*:!CVS:!thumbs.db:!picasa.ini:!*~"><source path="D:\Research\android\lib_interpreter\src\main\res"/><source path="D:\Research\android\lib_interpreter\build\generated\res\rs\debug"/><source path="D:\Research\android\lib_interpreter\build\generated\res\resValues\debug"/></dataSet><dataSet aapt-namespace="http://schemas.android.com/apk/res-auto" config="main" generated-set="main$Generated" ignore_pattern="!.svn:!.git:!.ds_store:!*.scc:.*:&lt;dir>_*:!CVS:!thumbs.db:!picasa.ini:!*~"><source path="D:\Research\android\lib_interpreter\src\main\res"/><source path="D:\Research\android\lib_interpreter\build\generated\res\rs\debug"/><source path="D:\Research\android\lib_interpreter\build\generated\res\resValues\debug"/></dataSet><dataSet aapt-namespace="http://schemas.android.com/apk/res-auto" config="debug$Generated" generated="true" ignore_pattern="!.svn:!.git:!.ds_store:!*.scc:.*:&lt;dir>_*:!CVS:!thumbs.db:!picasa.ini:!*~"><source path="D:\Research\android\lib_interpreter\src\debug\res"/></dataSet><dataSet aapt-namespace="http://schemas.android.com/apk/res-auto" config="debug" generated-set="debug$Generated" ignore_pattern="!.svn:!.git:!.ds_store:!*.scc:.*:&lt;dir>_*:!CVS:!thumbs.db:!picasa.ini:!*~"><source path="D:\Research\android\lib_interpreter\src\debug\res"/></dataSet><mergedItems/></merger>
\ No newline at end of file
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="org.tensorflow.lite.examples.imagesegmentation.tflite"
android:versionCode="1"
android:versionName="1.0" > <!-- Do not remove, it is needed for internal build system -->
<uses-sdk
android:minSdkVersion="21"
android:targetSdkVersion="29" />
</manifest>
\ No newline at end of file
1<?xml version="1.0" encoding="utf-8"?>
2<manifest xmlns:android="http://schemas.android.com/apk/res/android"
3 package="org.tensorflow.lite.examples.imagesegmentation.tflite"
4 android:versionCode="1"
5 android:versionName="1.0" > <!-- Do not remove, it is needed for internal build system -->
6 <uses-sdk
6-->D:\Research\android\lib_interpreter\src\main\AndroidManifest.xml:5:5-17
7 android:minSdkVersion="21"
7-->D:\Research\android\lib_interpreter\src\main\AndroidManifest.xml:5:5-17
8 android:targetSdkVersion="29" />
8-->D:\Research\android\lib_interpreter\src\main\AndroidManifest.xml:5:5-17
9
10</manifest>
{
"version": 1,
"applicationId": "org.tensorflow.lite.examples.imagesegmentation.tflite",
"variantType": "LIBRARY",
"elements": [
{
"outputType": {
"type": "MERGED_MANIFESTS"
},
"apkData": {
"type": "MAIN",
"splits": [],
"versionCode": 1,
"versionName": "1.0",
"outputFile": "lib_interpreter-debug.aar",
"fullName": "debug",
"baseName": "debug",
"dirName": ""
},
"path": "../../library_manifest/debug/AndroidManifest.xml",
"properties": {
"packageId": "org.tensorflow.lite.examples.imagesegmentation.tflite",
"split": ""
}
}
]
}
\ No newline at end of file
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment