Browse Source

add, delete and partly update area

master
Felix Diemar 3 years ago
parent
commit
489fd26187
19 changed files with 1209 additions and 207 deletions
  1. 1
    0
      Code Android/meinWald/app/build.gradle
  2. 1
    2
      Code Android/meinWald/app/src/main/AndroidManifest.xml
  3. 0
    18
      Code Android/meinWald/app/src/main/java/com/example/meinwald/MyApplication.java
  4. 149
    26
      Code Android/meinWald/app/src/main/java/com/example/meinwald/ui/area/AreaAdapter.java
  5. 137
    57
      Code Android/meinWald/app/src/main/java/com/example/meinwald/ui/area/AreaFragment.java
  6. 2
    2
      Code Android/meinWald/app/src/main/java/com/example/meinwald/ui/area/LocationService.java
  7. 247
    18
      Code Android/meinWald/app/src/main/java/com/example/meinwald/ui/area/OwnArea.java
  8. 96
    9
      Code Android/meinWald/app/src/main/java/com/example/meinwald/ui/map/MapsFragment.java
  9. 62
    0
      Code Android/meinWald/app/src/main/java/com/example/meinwald/ui/task/OwnTask.java
  10. 153
    2
      Code Android/meinWald/app/src/main/java/com/example/meinwald/ui/task/TaskAdapter.java
  11. 33
    44
      Code Android/meinWald/app/src/main/java/com/example/meinwald/ui/task/TasksFragment.java
  12. 43
    4
      Code Android/meinWald/app/src/main/res/layout/area_element.xml
  13. 66
    9
      Code Android/meinWald/app/src/main/res/layout/area_input.xml
  14. 40
    5
      Code Android/meinWald/app/src/main/res/layout/area_management.xml
  15. 7
    2
      Code Android/meinWald/app/src/main/res/layout/image_large.xml
  16. 22
    6
      Code Android/meinWald/app/src/main/res/layout/task_element.xml
  17. 0
    2
      Code Android/meinWald/app/src/main/res/layout/task_input.xml
  18. 144
    0
      Code Android/meinWald/app/src/main/res/layout/task_management.xml
  19. 6
    1
      Code Android/meinWald/app/src/main/res/values/colors.xml

+ 1
- 0
Code Android/meinWald/app/build.gradle View File

testImplementation 'junit:junit:4.12' testImplementation 'junit:junit:4.12'
androidTestImplementation 'androidx.test.ext:junit:1.1.2' androidTestImplementation 'androidx.test.ext:junit:1.1.2'
androidTestImplementation 'androidx.test.espresso:espresso-core:3.3.0' androidTestImplementation 'androidx.test.espresso:espresso-core:3.3.0'
compile 'com.google.maps.android:android-maps-utils:0.6.2'


} }

+ 1
- 2
Code Android/meinWald/app/src/main/AndroidManifest.xml View File

package="com.example.meinwald"> package="com.example.meinwald">


<application <application
android:name="com.example.meinwald.MyApplication"
android:allowBackup="true" android:allowBackup="true"
android:icon="@mipmap/ic_launcher" android:icon="@mipmap/ic_launcher"
android:label="@string/app_name" android:label="@string/app_name"
android:value="@string/google_maps_key" /> android:value="@string/google_maps_key" />


<service <service
android:name=".ui.area.LocationTrack"
android:name=".ui.area.LocationService"
android:exported="false"> android:exported="false">
</service> </service>



+ 0
- 18
Code Android/meinWald/app/src/main/java/com/example/meinwald/MyApplication.java View File

package com.example.meinwald;

import android.app.Application;
import android.content.Context;

public class MyApplication extends Application {

private static Context context;

public void onCreate() {
super.onCreate();
MyApplication.context = getApplicationContext();
}

public static Context getAppContext() {
return MyApplication.context;
}
}

+ 149
- 26
Code Android/meinWald/app/src/main/java/com/example/meinwald/ui/area/AreaAdapter.java View File

import android.app.AlertDialog; import android.app.AlertDialog;
import android.content.Context; import android.content.Context;
import android.content.DialogInterface; import android.content.DialogInterface;
import android.graphics.Rect;
import android.database.DataSetObserver;
import android.os.Build;
import android.util.Log; import android.util.Log;
import android.view.Gravity; import android.view.Gravity;
import android.view.LayoutInflater; import android.view.LayoutInflater;


import com.example.meinwald.BuildConfig; import com.example.meinwald.BuildConfig;
import com.example.meinwald.R; import com.example.meinwald.R;
import com.example.meinwald.ui.task.OwnTask;
import com.google.android.material.floatingactionbutton.FloatingActionButton;


import java.util.ArrayList; import java.util.ArrayList;
import java.util.Date;
import java.util.List; import java.util.List;


import androidx.appcompat.widget.AlertDialogLayout;
import androidx.appcompat.widget.LinearLayoutCompat;
import androidx.annotation.RequiresApi;
import androidx.constraintlayout.widget.ConstraintLayout; import androidx.constraintlayout.widget.ConstraintLayout;


import static java.security.AccessController.getContext;

public class AreaAdapter extends BaseAdapter public class AreaAdapter extends BaseAdapter
{ {
private final static String TAG = AreaAdapter.class.getSimpleName();

List<OwnArea> areaList; List<OwnArea> areaList;
LayoutInflater inflater; LayoutInflater inflater;
Context context; Context context;
boolean deleted = false;
Integer deletedPosition = null;


public AreaAdapter(Context applicationContext, List<OwnArea> areaList) public AreaAdapter(Context applicationContext, List<OwnArea> areaList)
{ {
} }


@Override @Override
public View getView(final int i, View view, final ViewGroup viewGroup) {
public View getView(final int i, final View view, final ViewGroup viewGroup) {


view = inflater.inflate(R.layout.area_element, null);
final ConstraintLayout elementView = view.findViewById(R.id.areaElement);
final ConstraintLayout infovView = view.findViewById(R.id.areaInfoView);
final TextView title = (TextView) view.findViewById(R.id.areaInfoTitle);
final TextView notice = (TextView) view.findViewById(R.id.areaInfoNotice);
final ImageView icon = (ImageView) view.findViewById(R.id.areaIcon);
final ImageView manageArea = (ImageView) view.findViewById(R.id.areaManageArea);
final View areaView = inflater.inflate(R.layout.area_element, null);
final ConstraintLayout elementView = areaView.findViewById(R.id.areaElement);
final ConstraintLayout infovView = areaView.findViewById(R.id.areaInfoView);
final TextView title = (TextView) areaView.findViewById(R.id.areaInfoTitle);
final TextView notice = (TextView) areaView.findViewById(R.id.areaInfoNotice);
final TextView area = (TextView) areaView.findViewById(R.id.areaInfoArea);
final ImageView icon = (ImageView) areaView.findViewById(R.id.areaIcon);
final ImageView manageArea = (ImageView) areaView.findViewById(R.id.areaManageArea);


context = view.getContext();

if (BuildConfig.DEBUG)
{
Log.d("AreaAdapter",areaList.get(i).toString());
Log.d("AreaAdapter",areaList.get(i).getTitle());
Log.d("AreaAdapter",areaList.get(i).getNotice());
}
context = areaView.getContext();


title.setText(areaList.get(i).getTitle()); title.setText(areaList.get(i).getTitle());
notice.setText(areaList.get(i).getNotice()); notice.setText(areaList.get(i).getNotice());
icon.setImageBitmap(areaList.get(i).getImage()); icon.setImageBitmap(areaList.get(i).getImage());


if (areaList.get(i).getArea() != null)
{
area.setText(String. format("%.2f", areaList.get(i).getArea()) + " Quadratmeter");
}

manageArea.setOnClickListener(new View.OnClickListener() { manageArea.setOnClickListener(new View.OnClickListener() {
@RequiresApi(api = Build.VERSION_CODES.JELLY_BEAN_MR1)
@Override @Override
public void onClick(View v) public void onClick(View v)
{ {
final View viewInflated = LayoutInflater.from(v.getRootView().getContext()).inflate(R.layout.area_management, viewGroup, false); final View viewInflated = LayoutInflater.from(v.getRootView().getContext()).inflate(R.layout.area_management, viewGroup, false);


builder.setView(viewInflated); builder.setView(viewInflated);
builder.setCancelable(true);


//get elements //get elements
TextView title = viewInflated.findViewById(R.id.areaManageTitle); TextView title = viewInflated.findViewById(R.id.areaManageTitle);
final TextView notice = viewInflated.findViewById(R.id.areaManageNotice); final TextView notice = viewInflated.findViewById(R.id.areaManageNotice);
TextView gpscount = viewInflated.findViewById(R.id.areaManageGPSPoints); TextView gpscount = viewInflated.findViewById(R.id.areaManageGPSPoints);
ImageView image = (ImageView) viewInflated.findViewById(R.id.areaManageImage); ImageView image = (ImageView) viewInflated.findViewById(R.id.areaManageImage);
final TextView lastChecked = viewInflated.findViewById(R.id.areaManagementLastChecked);


ImageView newNotice = (ImageView) viewInflated.findViewById(R.id.areaManageNewDescription); ImageView newNotice = (ImageView) viewInflated.findViewById(R.id.areaManageNewDescription);
ImageView newGPS = (ImageView) viewInflated.findViewById(R.id.areaManageNewGPS); ImageView newGPS = (ImageView) viewInflated.findViewById(R.id.areaManageNewGPS);
ImageView newImage = (ImageView) viewInflated.findViewById(R.id.areaManageNewImage); ImageView newImage = (ImageView) viewInflated.findViewById(R.id.areaManageNewImage);
ImageView deleteArea = (ImageView) viewInflated.findViewById(R.id.areaManageDeleteArea); ImageView deleteArea = (ImageView) viewInflated.findViewById(R.id.areaManageDeleteArea);
ImageView newDate = (ImageView) viewInflated.findViewById(R.id.areaManageNewDate);


//set current vlues
//set current values
title.setText(areaList.get(i).getTitle()); title.setText(areaList.get(i).getTitle());
notice.setText(areaList.get(i).getNotice()); notice.setText(areaList.get(i).getNotice());
gpscount.setText(String.valueOf(areaList.get(i).getLocations().size()));
if (areaList.get(i).getCheckHistory() != null)
{
lastChecked.setText(areaList.get(i).parseAndFormatLastCheckUpdate());
}

if (areaList.get(i).getLocations() != null)
{
gpscount.setText(String.valueOf(areaList.get(i).getLocations().size()));
}
else
{
gpscount.setText(String.valueOf(0));
}



if (areaList.get(i).getImage() != null) if (areaList.get(i).getImage() != null)
{ {
newbuilder.setView(viewInflated); newbuilder.setView(viewInflated);


final TextView noticeView = viewInflated.findViewById(R.id.areaManagementNoticeUserInput); final TextView noticeView = viewInflated.findViewById(R.id.areaManagementNoticeUserInput);
noticeView.setText(areaList.get(i).getNotice());


newbuilder.setPositiveButton("Bestätigen", new DialogInterface.OnClickListener() { newbuilder.setPositiveButton("Bestätigen", new DialogInterface.OnClickListener() {
@Override @Override
newbuilder.show(); newbuilder.show();
}}); }});


newDate.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
final AlertDialog.Builder newbuilder = new AlertDialog.Builder(v.getRootView().getContext());

newbuilder.setTitle("Neu Kontrolle hinzufügen?");

newbuilder.setPositiveButton("Bestätigen", new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
areaList.get(i).addCheckDate(new Date());
lastChecked.setText(areaList.get(i).parseAndFormatLastCheckUpdate());

//notifyDataSetChanged();

if (BuildConfig.DEBUG) {
for (OwnArea area : areaList) {
Log.d(TAG, "areaList item: " + area.toString());
}
}

dialog.dismiss();
}
});

newbuilder.setNegativeButton("Abbrechen", new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
dialog.cancel();
}
});

newbuilder.show();
}});

deleteArea.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(final View v) {
final AlertDialog.Builder newbuilder = new AlertDialog.Builder(v.getRootView().getContext());

newbuilder.setTitle("Das Grundstück wirklich löschen?");

newbuilder.setPositiveButton("Bestätigen", new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {

areaList.get(i).deleteFromExternalStorage(context);
areaList.remove(i);

notifyDataSetChanged();

if (BuildConfig.DEBUG)
{
for (OwnArea area: areaList)
{
Log.d(TAG, "areaList item: " + area.toString());
}
}

dialog.dismiss();

((ViewGroup)viewInflated.getParent()).removeView(viewInflated);
builder.show().cancel();
}
});

newbuilder.setNegativeButton("Abbrechen", new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
dialog.cancel();
}
});

newbuilder.show();
}});




builder.setPositiveButton("Bestätigen", new DialogInterface.OnClickListener() { builder.setPositiveButton("Bestätigen", new DialogInterface.OnClickListener() {
@Override @Override
public void onClick(DialogInterface dialog, int which) { public void onClick(DialogInterface dialog, int which) {


if (areaList.size() > i && areaList.get(i) != null)
{
if (BuildConfig.DEBUG)
{
Log.d(TAG, "update area: " + areaList.get(i).toString());
}
areaList.get(i).deleteFromExternalStorage(context);
areaList.get(i).writeToExternalStorage(context);
}

if (BuildConfig.DEBUG)
{
for (OwnArea area: areaList)
{
Log.d(TAG, "areaList item: " + area.toString());
}
}

dialog.dismiss(); dialog.dismiss();

} }
}); });


} }
}); });


return view;
return areaView;
}

public boolean isDeleted() {
return deleted;
}

public Integer getDeletedPosition()
{
return deletedPosition;
} }


@Override @Override

+ 137
- 57
Code Android/meinWald/app/src/main/java/com/example/meinwald/ui/area/AreaFragment.java View File

import android.app.AlertDialog; import android.app.AlertDialog;
import android.content.DialogInterface; import android.content.DialogInterface;
import android.content.pm.PackageManager; import android.content.pm.PackageManager;
import android.database.DataSetObserver;
import android.location.Location;
import android.os.Bundle; import android.os.Bundle;
import android.os.PowerManager; import android.os.PowerManager;
import android.preference.PreferenceManager; import android.preference.PreferenceManager;
import com.example.meinwald.R; import com.example.meinwald.R;
import com.google.android.gms.location.FusedLocationProviderClient; import com.google.android.gms.location.FusedLocationProviderClient;
import com.google.android.gms.location.LocationServices; import com.google.android.gms.location.LocationServices;
import com.google.android.gms.maps.CameraUpdateFactory;
import com.google.android.gms.maps.model.LatLng; import com.google.android.gms.maps.model.LatLng;
import com.google.android.gms.tasks.OnCompleteListener;
import com.google.android.gms.tasks.Task;
import com.google.android.material.floatingactionbutton.FloatingActionButton; import com.google.android.material.floatingactionbutton.FloatingActionButton;


import org.json.JSONArray; import org.json.JSONArray;
* LOCATION * LOCATION
*/ */
private static final int PERMISSIONS_REQUEST_ACCESS_FINE_LOCATION = 1; private static final int PERMISSIONS_REQUEST_ACCESS_FINE_LOCATION = 1;
/**
* The geographical location where the device is currently located.
* That is the last-known location retrieved by the Fused Location Provider.
*/
private Location mLastKnownLocation;
/** /**
* The entry point to the Fused Location Provider. * The entry point to the Fused Location Provider.
*/ */


//get saved areas //get saved areas
allAreas = loadAreasFromPreferences(); allAreas = loadAreasFromPreferences();
for (int i = 0; i < allAreas.size(); i++)
{
allAreas.get(i).setPathFile(areaReferences.get(i).getPath());
}
instantiateAreasList(); instantiateAreasList();


PowerManager powerManager = (PowerManager) getContext().getSystemService(POWER_SERVICE); PowerManager powerManager = (PowerManager) getContext().getSystemService(POWER_SERVICE);
AlertDialog.Builder builder = new AlertDialog.Builder(getContext()); AlertDialog.Builder builder = new AlertDialog.Builder(getContext());


newArea = new OwnArea(); newArea = new OwnArea();
newPositions = new ArrayList<>();


final View viewInflated = LayoutInflater.from(getContext()).inflate(R.layout.area_input, (ViewGroup) getView(), false); final View viewInflated = LayoutInflater.from(getContext()).inflate(R.layout.area_input, (ViewGroup) getView(), false);
builder.setView(viewInflated); builder.setView(viewInflated);


final Button startTracking = viewInflated.findViewById(R.id.areaStartTracking); final Button startTracking = viewInflated.findViewById(R.id.areaStartTracking);
final Button stopTracking = viewInflated.findViewById(R.id.areaStopTracking); final Button stopTracking = viewInflated.findViewById(R.id.areaStopTracking);
final Button addLocation = viewInflated.findViewById(R.id.areaAddGPSPoint);


startTracking.setOnClickListener(new View.OnClickListener() { startTracking.setOnClickListener(new View.OnClickListener() {
@Override @Override


startTracking.setVisibility(View.INVISIBLE); startTracking.setVisibility(View.INVISIBLE);
stopTracking.setVisibility(View.VISIBLE); stopTracking.setVisibility(View.VISIBLE);
addLocation.setVisibility(View.INVISIBLE);
} }
}); });


public void onClick(View view) { public void onClick(View view) {


//stop tracking //stop tracking
newPositions = gps.getPositions();
List<LatLng> positionsToAdd = new ArrayList<>();
positionsToAdd = gps.getPositions();

for (LatLng pos: positionsToAdd)
{
newPositions.add(pos);
}


if (BuildConfig.DEBUG) if (BuildConfig.DEBUG)
{ {
Log.d(TAG, "Received locations: " + newPositions.size()); Log.d(TAG, "Received locations: " + newPositions.size());
} }


newArea.setLocations(newPositions);
wakeLock.release(); wakeLock.release();


startTracking.setVisibility(View.VISIBLE); startTracking.setVisibility(View.VISIBLE);
stopTracking.setVisibility(View.INVISIBLE); stopTracking.setVisibility(View.INVISIBLE);
addLocation.setVisibility(View.VISIBLE);
} }
}); });


addLocation.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {

//get last known location
getDeviceLocation();
}});

builder.setPositiveButton("Bestätigen", new DialogInterface.OnClickListener() { builder.setPositiveButton("Bestätigen", new DialogInterface.OnClickListener() {
@Override @Override
public void onClick(DialogInterface dialog, int which) { public void onClick(DialogInterface dialog, int which) {
//save user input //save user input
newArea.setTitle(String.valueOf(titleView.getText())); newArea.setTitle(String.valueOf(titleView.getText()));
newArea.setNotice(String.valueOf(noticeView.getText())); newArea.setNotice(String.valueOf(noticeView.getText()));
newArea.setLocations(newPositions);
newArea.calculateArea();


boolean result = allAreas.add(newArea); boolean result = allAreas.add(newArea);


Log.d(TAG, "add new task result: " + result); Log.d(TAG, "add new task result: " + result);
} }


emptyPreferencesAndSaveAreaReferencesToPreferences();
newArea.writeToExternalStorage(getContext());
areaReferences.add(new AreaReference(newArea.getId(), newArea.getPathFile()));


areaReferences.add(new AreaReference(newArea.getId(), writeAreaToExternalStorage(newArea)));
emptyPreferencesAndSaveAreaReferencesToPreferences();


//actuate list //actuate list
instantiateAreasList(); instantiateAreasList();


builder.setNegativeButton("Abbrechen", new DialogInterface.OnClickListener() { builder.setNegativeButton("Abbrechen", new DialogInterface.OnClickListener() {
@Override @Override
public void onClick(DialogInterface dialog, int which) {
public void onClick(DialogInterface dialog, int which)
{
//reset variables
newArea = new OwnArea();
newPositions = new ArrayList<>();

dialog.cancel(); dialog.cancel();
} }
}); });
public void instantiateAreasList() public void instantiateAreasList()
{ {
final AreaAdapter adapter = new AreaAdapter(getActivity().getApplicationContext(), allAreas); final AreaAdapter adapter = new AreaAdapter(getActivity().getApplicationContext(), allAreas);
adapter.registerDataSetObserver(new DataSetObserver() {
@Override
public void onChanged() {
super.onChanged();

if (BuildConfig.DEBUG)
{
Log.d(TAG, "onChanged");
}

if (BuildConfig.DEBUG)
{
Log.d(TAG, "dataset size: " + areaList.getAdapter().getCount());
}

if (areaList.getAdapter().getCount() > 0)
{
allAreas = new ArrayList<>();
areaReferences =new ArrayList<>();

for (int i = 0; i < areaList.getAdapter().getCount(); i++)
{
allAreas.add((OwnArea) areaList.getAdapter().getItem(i));
if (BuildConfig.DEBUG)
{
Log.d(TAG, "dataset added: " + allAreas.get(i).toString());
}

areaReferences.add(new AreaReference(allAreas.get(i).getId(), allAreas.get(i).getPathFile()));
}
}
}
});
areaList.setAdapter(adapter); areaList.setAdapter(adapter);


//initialise onClickListeners //initialise onClickListeners
return areas; return areas;
} }


/**
* Save OwnArea object in textfile on external storage.
*
* @param newArea OwnArea object to write to file.
* @return
*/
private String writeAreaToExternalStorage(OwnArea newArea){

if (BuildConfig.DEBUG)
{
Log.d(TAG, "writeAreaToExternalStorage()");
}

// Find the root of the external storage.
File root = android.os.Environment.getExternalStorageDirectory();

//create file if it does not exist
File path = new File (getContext().getFilesDir(), "meinWald" + File.pathSeparator + "areas");
if(!path.exists()){
path.mkdirs();
if (BuildConfig.DEBUG)
{
Log.d(TAG, "Create new text file: " + path);
}
}
File file = new File(path, newArea.getId() + ".txt");

//open file and write to it
try {
FileOutputStream f = new FileOutputStream(file);
PrintWriter pw = new PrintWriter(f);
pw.print(areaToString(newArea));
pw.close();
f.close();
} catch (FileNotFoundException e) {
if (BuildConfig.DEBUG)
{
Log.e(TAG, "Failed write to external storage: " + e.toString());
}
} catch (IOException e) {
if (BuildConfig.DEBUG)
{
Log.e(TAG, "Failed write to external storage: " + e.toString());
}
}

return file.getPath();
}

/** /**
* Read OwnArea from file in external storage and return as a string. * Read OwnArea from file in external storage and return as a string.
* *


while ((line = br.readLine()) != null) { while ((line = br.readLine()) != null) {
text.append(line); text.append(line);
if (BuildConfig.DEBUG)
{
Log.d(TAG, "Line: " + line);
}
} }
br.close(); br.close();
} }
String jsonString = PreferenceManager.getDefaultSharedPreferences(getContext()).getString(KEY_AREA_REFERENCES, "error"); String jsonString = PreferenceManager.getDefaultSharedPreferences(getContext()).getString(KEY_AREA_REFERENCES, "error");
if(!"error".equalsIgnoreCase(jsonString)) { if(!"error".equalsIgnoreCase(jsonString)) {
JSONArray jsonObjects = new JSONArray(jsonString); JSONArray jsonObjects = new JSONArray(jsonString);
for (int i = 0; i<jsonObjects.length();i++) {
for (int i = 0; i<jsonObjects.length();i++)
{
areas.add(new AreaReference(jsonObjects.getJSONObject(i))); areas.add(new AreaReference(jsonObjects.getJSONObject(i)));

// Find the root of the external storage.
File root = android.os.Environment.getExternalStorageDirectory();

//delete reference if file does not exist
File file = new File(getContext().getFilesDir(), "meinWald" + File.pathSeparator + "areas" + File.pathSeparator + areas.get(i).getId() + ".txt");
if(file.exists())
{
areas.remove(i);
}
} }
} }
else else
} }


/** /**
* Saves epicolors to preferences
* Saves areas to preferences
*/ */
private void emptyPreferencesAndSaveAreaReferencesToPreferences() private void emptyPreferencesAndSaveAreaReferencesToPreferences()
{ {


} }


/**
* Get the best and most recent location of the device, which may be null in rare
* cases when a location is not available.
*
*/
private void getDeviceLocation() {
try {
if (mLocationPermissionGranted) {
Task<Location> locationResult = mFusedLocationProviderClient.getLastLocation();
locationResult.addOnCompleteListener(getActivity(), new OnCompleteListener<Location>() {
@Override
public void onComplete(@NonNull Task<Location> task) {
if (task.isSuccessful())
{
// Set the last known position to the current location of the device and add to tracking stack
mLastKnownLocation = task.getResult();
newPositions.add(new LatLng(mLastKnownLocation.getLatitude(),mLastKnownLocation.getLongitude()));

if (BuildConfig.DEBUG) {

if (task.getResult() != null)
{
Log.d(TAG, "getDeviceLocation: " + task.getResult().toString());
Log.d(TAG, "Size: " + newPositions.size());
}
}
} else {
if (BuildConfig.DEBUG) {
Log.d(TAG, "Current location is null. Using defaults.");
Log.e(TAG, "Exception: %s", task.getException());
}
}
}
});
}
} catch (SecurityException e) {
if (BuildConfig.DEBUG) {
Log.e(TAG, "Exception occurred: ");
e.printStackTrace();
}
}
}

public void startLocationTracking(){ public void startLocationTracking(){


final Runnable runnable= new Runnable() { final Runnable runnable= new Runnable() {

+ 2
- 2
Code Android/meinWald/app/src/main/java/com/example/meinwald/ui/area/LocationService.java View File

private static final long MIN_DISTANCE_CHANGE_FOR_UPDATES = 1; // 5 meters private static final long MIN_DISTANCE_CHANGE_FOR_UPDATES = 1; // 5 meters


// The minimum time between updates in milliseconds // The minimum time between updates in milliseconds
private static final long MIN_TIME_BW_UPDATES = 1000 * 5 * 1; // 5 seconds
private static final long MIN_TIME_BW_UPDATES = 1000 * 1 * 1; // 5 seconds


// Declaring a Location Manager // Declaring a Location Manager
protected LocationManager mLocationManager; protected LocationManager mLocationManager;
Log.d(TAG, "onLocationChanged(), new location: " + location.toString()); Log.d(TAG, "onLocationChanged(), new location: " + location.toString());
} }


positions.add(new LatLng(location.getLatitude(), getLongitude()));
positions.add(new LatLng(location.getLatitude(), location.getLongitude()));
} }


@Override @Override

+ 247
- 18
Code Android/meinWald/app/src/main/java/com/example/meinwald/ui/area/OwnArea.java View File

package com.example.meinwald.ui.area; package com.example.meinwald.ui.area;


import android.content.Context;
import android.graphics.Bitmap; import android.graphics.Bitmap;
import android.location.Location;
import android.util.Log; import android.util.Log;


import com.example.meinwald.BuildConfig; import com.example.meinwald.BuildConfig;
import com.google.android.gms.maps.model.LatLng; import com.google.android.gms.maps.model.LatLng;
import com.google.maps.android.SphericalUtil;


import org.json.JSONArray; import org.json.JSONArray;
import org.json.JSONException; import org.json.JSONException;
import org.json.JSONObject; import org.json.JSONObject;


import java.sql.Time;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.PrintWriter;
import java.text.SimpleDateFormat;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.Calendar;
import java.util.Date; import java.util.Date;
import java.util.List; import java.util.List;


private List<LatLng> locations; private List<LatLng> locations;
private Bitmap image; private Bitmap image;
private String pathImage; private String pathImage;
private String pathLocations;
private String pathFile;
private String id; private String id;
private List<Date> checkHistory;
private Double area;


public void setImage(Bitmap image) { public void setImage(Bitmap image) {
this.image = image; this.image = image;
this.pathImage = pathImage; this.pathImage = pathImage;
} }


public void setPathLocations(String pathLocations) {
this.pathLocations = pathLocations;
public void setPathFile(String pathFile) {
this.pathFile = pathFile;
}

public Double getArea() {
return area;
}

public void setArea(Double area) {
this.area = area;
}

public void calculateArea()
{
this.area = SphericalUtil.computeArea(this.locations);
} }


public String getNotice() { public String getNotice() {
return pathImage; return pathImage;
} }


public String getPathLocations() {
return pathLocations;
public String getPathFile() {
return pathFile;
} }


public OwnArea()
public List<Date> getCheckHistory() {
return checkHistory;
}

public void setCheckHistory(List<Date> checkHistory) {
this.checkHistory = checkHistory;
}

public void addCheckDate(Date newDate)
{ {
if (BuildConfig.DEBUG)
{
Log.d(getClass().getSimpleName(), "add DATE");
}
if(this.checkHistory == null)
{
this.checkHistory = new ArrayList<>();
}


this.checkHistory.add(newDate);
}

public OwnArea()
{
this.title = null;
this.id = null;
this.notice = null;
this.pathFile = null;
this.image = null;
this.pathImage = null;
this.locations = new ArrayList<>();
this.checkHistory = new ArrayList<>();
} }


public OwnArea(String jsonString){
public OwnArea(String jsonString)
{
this.checkHistory = new ArrayList<>();
this.locations = new ArrayList<>();

try { try {
JSONObject areaObject = new JSONObject(jsonString); JSONObject areaObject = new JSONObject(jsonString);
this.title = areaObject.getString("title"); this.title = areaObject.getString("title");
} }
} }


String historyString = areaObject.getString("history");
JSONArray history = new JSONArray(historyString);
this.checkHistory = new ArrayList<>();

for (int i = 0; i<history.length();i++) {
this.checkHistory.add(new Date(history.getJSONObject(i).getLong("date")));

if (BuildConfig.DEBUG)
{
Log.d(getClass().getSimpleName(), "read location: " + this.checkHistory.get(i).toString());
}
}

if (this.locations != null && this.locations.size()>2)
{
calculateArea();
}

} catch (JSONException e) { } catch (JSONException e) {
if (BuildConfig.DEBUG) { if (BuildConfig.DEBUG) {
Log.e(this.getClass().getSimpleName(), "area json: " + jsonString); Log.e(this.getClass().getSimpleName(), "area json: " + jsonString);
return id; return id;
} }


/**
* Save OwnArea object in textfile on external storage.
*
* @return
*/
public void writeToExternalStorage(Context context){

if (BuildConfig.DEBUG)
{
Log.d(getClass().getSimpleName(), "writeAreaToExternalStorage()");
}

// Find the root of the external storage.
File root = android.os.Environment.getExternalStorageDirectory();

//create file if it does not exist
File path = new File (context.getFilesDir(), "meinWald" + File.pathSeparator + "areas");
if(!path.exists()){
path.mkdirs();
if (BuildConfig.DEBUG)
{
Log.d(getClass().getSimpleName(), "Create new text file: " + path);
}
}
File file = new File(path, this.getId() + ".txt");

//open file and write to it
try {
FileOutputStream f = new FileOutputStream(file);
PrintWriter pw = new PrintWriter(f);
pw.print(this.toJSONObject());
if (BuildConfig.DEBUG)
{
Log.d(getClass().getSimpleName(), "Json to write in file: " + this.toJSONObject().toString());
}
pw.close();
f.close();
} catch (FileNotFoundException e) {
if (BuildConfig.DEBUG)
{
Log.e(getClass().getSimpleName(), "Failed write to external storage: " + e.toString());
}
} catch (IOException e) {
if (BuildConfig.DEBUG)
{
Log.e(getClass().getSimpleName(), "Failed write to external storage: " + e.toString());
}
}

this.pathFile = file.getPath();
}

/**
* Delete OwnArea object textfile from external storage.
*/
public void deleteFromExternalStorage(Context context)
{
if (BuildConfig.DEBUG)
{
Log.d(getClass().getSimpleName(), "deleteFromExternalStorage()");
}

// Find the root of the external storage.
File root = android.os.Environment.getExternalStorageDirectory();

//delete file if exists
File file = new File(context.getFilesDir(), "meinWald" + File.pathSeparator + "areas" + File.pathSeparator + this.getId() + ".txt");
if(!file.exists()){

file.delete();

if (BuildConfig.DEBUG)
{
Log.d(getClass().getSimpleName(), "Delete text file: " + file.getPath());
}
}

}



/** /**
* Returns OwnArea as JSONObject. * Returns OwnArea as JSONObject.
//convert all locations //convert all locations
JSONArray writeObjects = new JSONArray(); JSONArray writeObjects = new JSONArray();


for (LatLng location: this.locations) {
if (BuildConfig.DEBUG) {
Log.d("OwnArea", "Save locations, locations size: " + locations.size());
}


JSONObject singleLocationObject = new JSONObject();
singleLocationObject.put("Lat", location.latitude);
singleLocationObject.put("Lng", location.longitude);
if (this.locations != null && this.locations.size() > 0)
{
for (LatLng location: this.locations) {


writeObjects.put(singleLocationObject);
JSONObject singleLocationObject = new JSONObject();
singleLocationObject.put("Lat", location.latitude);
singleLocationObject.put("Lng", location.longitude);


if (BuildConfig.DEBUG) {
Log.d("OwnArea", "added location object: " + singleLocationObject.toString());
writeObjects.put(singleLocationObject);

if (BuildConfig.DEBUG) {
Log.d("OwnArea", "added location object: " + singleLocationObject.toString());
}
} }
} }


object.put("locations", writeObjects.toString()); object.put("locations", writeObjects.toString());


//convert all locations
writeObjects = new JSONArray();

if (BuildConfig.DEBUG) {
Log.d("OwnArea", "Save history, history size: " + checkHistory.size());
}

if (this.checkHistory != null && this.checkHistory.size() > 0)
{
if (BuildConfig.DEBUG) {
Log.d("OwnArea", "history not empty");
}

for (Date date : this.checkHistory) {

JSONObject singleHistoryObject = new JSONObject();
singleHistoryObject.put("date", date.getTime());

writeObjects.put(singleHistoryObject);

if (BuildConfig.DEBUG) {
Log.d("OwnArea", "added history object: " + singleHistoryObject.toString());
}
}
}

object.put("history", writeObjects.toString());

if (area!=null)
{
object.put("area",this.area);
}
else
{
object.put("area", null);
}

return object; return object;


} catch (JSONException e) { } catch (JSONException e) {
if (BuildConfig.DEBUG) { if (BuildConfig.DEBUG) {
Log.e(this.getClass().getSimpleName(), Log.e(this.getClass().getSimpleName(),
String.format("Error while parsing epiColorDto to JSONObject. Values of epiColorDto: %s", this.toString()));
String.format("Error while parsing OwnArea to JSONObject. Values of OwnArea: %s", this.toString()));
} }
return null; return null;
} }
"title='" + title + '\'' + "title='" + title + '\'' +
", notice='" + notice + '\'' + ", notice='" + notice + '\'' +
", pathImage='" + pathImage + '\'' + ", pathImage='" + pathImage + '\'' +
", pathLocations='" + pathLocations + '\'' +
", pathLocations='" + pathFile + '\'' +
", id='" + id + '\'' + ", id='" + id + '\'' +
", dates='" + checkHistory.size() + '\'' +
'}'; '}';
} }

/**
* Parses last check update from milliseconds to string and formats it to "dd.MM.yyyy hh:mm".
*
* @return date parsed and mapped as string representation
*/
public String parseAndFormatLastCheckUpdate() {
SimpleDateFormat formatter = new SimpleDateFormat( "dd.MM.yyyy kk:mm");
Calendar calendar = Calendar.getInstance();
if (checkHistory != null && checkHistory.size()> 0)
{
calendar.setTimeInMillis(this.checkHistory.get(this.checkHistory.size()-1).getTime());
}
else
{
return "Keine Kontrolle vorhanden!";
}

return formatter.format(calendar.getTime());
}

public Long getLastChecked()
{
if (checkHistory != null && checkHistory.size()> 0)
{
return this.checkHistory.get(this.checkHistory.size()-1).getTime();
}
else
{
return (long) -1;
}
}
} }

+ 96
- 9
Code Android/meinWald/app/src/main/java/com/example/meinwald/ui/map/MapsFragment.java View File

import android.content.pm.PackageManager; import android.content.pm.PackageManager;
import android.graphics.Bitmap; import android.graphics.Bitmap;
import android.graphics.BitmapFactory; import android.graphics.BitmapFactory;
import android.graphics.Color;
import android.location.Location; import android.location.Location;
import android.os.Bundle; import android.os.Bundle;
import android.os.IBinder; import android.os.IBinder;
import android.view.View; import android.view.View;
import android.view.ViewGroup; import android.view.ViewGroup;
import android.widget.ListView; import android.widget.ListView;
import android.widget.Toast;


import com.example.meinwald.BuildConfig; import com.example.meinwald.BuildConfig;
import com.example.meinwald.R; import com.example.meinwald.R;
import com.example.meinwald.ui.area.AreaReference; import com.example.meinwald.ui.area.AreaReference;
import com.example.meinwald.ui.area.OwnArea; import com.example.meinwald.ui.area.OwnArea;
import com.example.meinwald.ui.task.OwnTask; import com.example.meinwald.ui.task.OwnTask;
import com.google.android.gms.common.util.Hex;
import com.google.android.gms.dynamic.IObjectWrapper; import com.google.android.gms.dynamic.IObjectWrapper;
import com.google.android.gms.location.FusedLocationProviderClient; import com.google.android.gms.location.FusedLocationProviderClient;
import com.google.android.gms.location.LocationServices; import com.google.android.gms.location.LocationServices;
import com.google.android.gms.maps.model.BitmapDescriptor; import com.google.android.gms.maps.model.BitmapDescriptor;
import com.google.android.gms.maps.model.CameraPosition; import com.google.android.gms.maps.model.CameraPosition;
import com.google.android.gms.maps.model.LatLng; import com.google.android.gms.maps.model.LatLng;
import com.google.android.gms.maps.model.Marker;
import com.google.android.gms.maps.model.MarkerOptions; import com.google.android.gms.maps.model.MarkerOptions;
import com.google.android.gms.maps.model.Polygon;
import com.google.android.gms.maps.model.PolygonOptions;
import com.google.android.gms.maps.model.Polyline; import com.google.android.gms.maps.model.Polyline;
import com.google.android.gms.maps.model.PolylineOptions; import com.google.android.gms.maps.model.PolylineOptions;
import com.google.android.gms.tasks.OnCompleteListener; import com.google.android.gms.tasks.OnCompleteListener;
import com.google.android.gms.tasks.Task; import com.google.android.gms.tasks.Task;
import com.google.maps.android.SphericalUtil;


import org.json.JSONArray; import org.json.JSONArray;
import org.json.JSONException; import org.json.JSONException;
import java.io.FileReader; import java.io.FileReader;
import java.io.IOException; import java.io.IOException;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.Date;
import java.util.List; import java.util.List;


import androidx.annotation.NonNull; import androidx.annotation.NonNull;
mFusedLocationProviderClient = LocationServices.getFusedLocationProviderClient(getActivity()); mFusedLocationProviderClient = LocationServices.getFusedLocationProviderClient(getActivity());


//wait for map is ready //wait for map is ready
mapFragment.getMapAsync(new OnMapReadyCallback() {
mapFragment.getMapAsync(new OnMapReadyCallback()
{
@Override @Override
public void onMapReady(GoogleMap googleMap) { public void onMapReady(GoogleMap googleMap) {
//save map instance locally //save map instance locally
mMap = googleMap; mMap = googleMap;
//set max zoom level //set max zoom level
mMap.setMaxZoomPreference(MAX_ZOOM); mMap.setMaxZoomPreference(MAX_ZOOM);
mMap.setMapType(GoogleMap.MAP_TYPE_HYBRID);
mMap.setOnMarkerClickListener(new GoogleMap.OnMarkerClickListener() {
@Override
public boolean onMarkerClick(Marker marker) {

if (mMap.getCameraPosition().zoom < 17.5)
{
mMap.moveCamera(CameraUpdateFactory.newLatLngZoom(new LatLng(marker.getPosition().latitude, marker.getPosition().longitude),(float)17.5));
}
else
{
mMap.moveCamera(CameraUpdateFactory.newLatLngZoom(new LatLng(marker.getPosition().latitude, marker.getPosition().longitude),mMap.getCameraPosition().zoom));
}

return false;
}
});


//retrieve saved instance state //retrieve saved instance state
mCameraPosition = parseCameraPosition(PreferenceManager.getDefaultSharedPreferences(getContext()).getString(KEY_CAMERA_POSITION, new CameraPosition(new LatLng(45.0,11.0), (float) 1.0, (float) 0.0,(float) 0.0).toString())); mCameraPosition = parseCameraPosition(PreferenceManager.getDefaultSharedPreferences(getContext()).getString(KEY_CAMERA_POSITION, new CameraPosition(new LatLng(45.0,11.0), (float) 1.0, (float) 0.0,(float) 0.0).toString()));
{ {
for (OwnArea area: allAreas) for (OwnArea area: allAreas)
{ {

PolylineOptions options = new PolylineOptions().clickable(true);

for (LatLng location: area.getLocations())
if (area.getLocations() != null && area.getLocations().size()>0)
{ {
options.add(location);
PolygonOptions options = new PolygonOptions().clickable(true);


if (BuildConfig.DEBUG) if (BuildConfig.DEBUG)
{ {
Log.d(TAG, "Position: " + location.toString());
Log.d(TAG, "Color: " + getAreaColor(area.getLastChecked()));
Log.d(TAG, "Color: " + String.valueOf(getAreaColor(area.getLastChecked() & 0x00FFFFFF) | 0x60000000));
Log.d(TAG, "Area: " + SphericalUtil.computeArea(area.getLocations()));
}
options.strokeColor(getAreaColor(area.getLastChecked()));
options.fillColor((options.getStrokeColor() & 0x00FFFFFF) | 0x60000000);

for (LatLng location: area.getLocations())
{
options.add(location);

if (BuildConfig.DEBUG)
{
Log.d(TAG, "Position: " + location.toString());
}
} }
}


Polyline polyline1 = mMap.addPolyline(options);
options.add(area.getLocations().get(0));


mMap.addPolygon(options);
}
} }
} }


drawAreas(); drawAreas();
} }


/**
* Decides color of area based on the time passed since last ckeck update.
*
* @param time difference in milliseconds between last check and now
* @return color number
*/
private int getAreaColor(long time) {
//set transparency related to time difference
if(time > -1)
{
long timeDiff = new Date().getTime() - time;

//less than a week
if (timeDiff < 7*24*60*60*1000L)
{
return Color.parseColor("#57a639");
}
//less than two weeks
else if (timeDiff < 14*24*60*60*1000L)
{
return Color.parseColor("#819b45");
}
//less than three weeks
else if (timeDiff < 21*24*60*60*1000L)
{
return Color.parseColor("#d3d30c");
}
//less than four weeks
else if (timeDiff < 28*24*60*60*1000L)
{
return Color.parseColor("#df9600");
}
//less than 6 weeks
else if (timeDiff < 42*24*60*60*1000L)
{
return Color.parseColor("#df3d00");
}
//longer than four weeks
else
{
return Color.parseColor("#f70000");
}
}
else
{
return Color.parseColor("#f70000");
}
}

/** /**
* Request read external storage permission, so that we can get saved images from external storage. * Request read external storage permission, so that we can get saved images from external storage.
* The result of the permission request is handled by a callback, * The result of the permission request is handled by a callback,

+ 62
- 0
Code Android/meinWald/app/src/main/java/com/example/meinwald/ui/task/OwnTask.java View File

package com.example.meinwald.ui.task; package com.example.meinwald.ui.task;


import android.content.Context;
import android.graphics.Bitmap; import android.graphics.Bitmap;
import android.location.Location; import android.location.Location;
import android.media.Image; import android.media.Image;
import org.json.JSONException; import org.json.JSONException;
import org.json.JSONObject; import org.json.JSONObject;


import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.util.Date; import java.util.Date;


public class OwnTask public class OwnTask


public void setPathImage(String pathImage) { this.pathImage = pathImage; } public void setPathImage(String pathImage) { this.pathImage = pathImage; }


public String saveImageToExternalStorage(Context context){

File path = null;

try {
path = new File(context.getFilesDir(), "meinWald" + File.separator + "Images");
if(!path.exists()){
path.mkdirs();
}

if (BuildConfig.DEBUG) {
Log.d(this.getClass().getSimpleName(), "Image file path: " + path);
}

File outFile = new File(path, this.id + ".jpeg");
if (!outFile.exists())
{
FileOutputStream outputStream = new FileOutputStream(outFile);
this.image.compress(Bitmap.CompressFormat.JPEG, 100, outputStream);
outputStream.close();
}

} catch (FileNotFoundException e) {
Log.e(this.getClass().getSimpleName(), "Saving received message failed with", e);
} catch (IOException e) {
Log.e(this.getClass().getSimpleName(), "Saving received message failed with", e);
}

return path.toString();
}

/**
* Delete OwnArea object textfile from external storage.
*/
public void deleteFromExternalStorage(Context context)
{
if (BuildConfig.DEBUG)
{
Log.d(getClass().getSimpleName(), "deleteFromExternalStorage()");
}

// Find the root of the external storage.
File root = android.os.Environment.getExternalStorageDirectory();

//delete file if exists
File file = new File(context.getFilesDir(), "meinWald" + File.pathSeparator + "Images" + File.pathSeparator + this.getId() + ".txt");
if(!file.exists()){

file.delete();

if (BuildConfig.DEBUG)
{
Log.d(getClass().getSimpleName(), "Delete image file: " + file.getPath());
}
}
}

@Override @Override
public String toString() { public String toString() {
return "OwnTask{" + return "OwnTask{" +

+ 153
- 2
Code Android/meinWald/app/src/main/java/com/example/meinwald/ui/task/TaskAdapter.java View File

import android.content.Context; import android.content.Context;
import android.content.DialogInterface; import android.content.DialogInterface;
import android.graphics.Rect; import android.graphics.Rect;
import android.os.Build;
import android.util.Log; import android.util.Log;
import android.view.LayoutInflater; import android.view.LayoutInflater;
import android.view.View; import android.view.View;


import com.example.meinwald.BuildConfig; import com.example.meinwald.BuildConfig;
import com.example.meinwald.R; import com.example.meinwald.R;
import com.example.meinwald.ui.area.AreaAdapter;
import com.example.meinwald.ui.area.OwnArea; import com.example.meinwald.ui.area.OwnArea;
import com.google.android.material.floatingactionbutton.FloatingActionButton; import com.google.android.material.floatingactionbutton.FloatingActionButton;


import java.util.ArrayList; import java.util.ArrayList;
import java.util.List; import java.util.List;


import androidx.annotation.RequiresApi;
import androidx.appcompat.widget.AlertDialogLayout; import androidx.appcompat.widget.AlertDialogLayout;
import androidx.appcompat.widget.LinearLayoutCompat; import androidx.appcompat.widget.LinearLayoutCompat;
import androidx.constraintlayout.widget.ConstraintLayout; import androidx.constraintlayout.widget.ConstraintLayout;


public class TaskAdapter extends BaseAdapter public class TaskAdapter extends BaseAdapter
{ {
private final static String TAG = TaskAdapter.class.getSimpleName();

List<OwnTask> taskList; List<OwnTask> taskList;
LayoutInflater inflater; LayoutInflater inflater;
Context context; Context context;
final TextView title = (TextView) view.findViewById(R.id.taskInfoTitle); final TextView title = (TextView) view.findViewById(R.id.taskInfoTitle);
final TextView notice = (TextView) view.findViewById(R.id.taskInfoNotice); final TextView notice = (TextView) view.findViewById(R.id.taskInfoNotice);
final ImageView icon = (ImageView) view.findViewById(R.id.taskIcon); final ImageView icon = (ImageView) view.findViewById(R.id.taskIcon);
final ImageView manageTask = (ImageView) view.findViewById(R.id.taskManageTask);
context = view.getContext(); context = view.getContext();




} }
}); });


manageTask.setOnClickListener(new View.OnClickListener() {
@RequiresApi(api = Build.VERSION_CODES.JELLY_BEAN_MR1)
@Override
public void onClick(View v)
{
final AlertDialog.Builder builder = new AlertDialog.Builder(v.getRootView().getContext());
final View viewInflated = LayoutInflater.from(v.getRootView().getContext()).inflate(R.layout.area_management, viewGroup, false);

builder.setView(viewInflated);

//get elements
TextView title = viewInflated.findViewById(R.id.areaManageTitle);
final TextView notice = viewInflated.findViewById(R.id.areaManageNotice);
TextView gps = viewInflated.findViewById(R.id.areaManageGPSPoints);
ImageView image = (ImageView) viewInflated.findViewById(R.id.areaManageImage);

ImageView newNotice = (ImageView) viewInflated.findViewById(R.id.areaManageNewDescription);
ImageView newGPS = (ImageView) viewInflated.findViewById(R.id.areaManageNewGPS);
ImageView newImage = (ImageView) viewInflated.findViewById(R.id.areaManageNewImage);
ImageView deleteArea = (ImageView) viewInflated.findViewById(R.id.areaManageDeleteArea);

//set current vlues
title.setText(taskList.get(i).getTitle());
notice.setText(taskList.get(i).getNotice());

if (taskList.get(i).getLocation() != null)
{
gps.setText(String.valueOf(taskList.get(i).getLocation()));
}
else
{
gps.setText("Kein Standort gespeichert!");
}

if (taskList.get(i).getImage() != null)
{
image.setImageBitmap(taskList.get(i).getImage());
}

newNotice.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v)
{
final AlertDialog.Builder newbuilder = new AlertDialog.Builder(v.getRootView().getContext());
final View viewInflated = LayoutInflater.from(v.getRootView().getContext()).inflate(R.layout.area_management_notice, viewGroup, false);

newbuilder.setView(viewInflated);

final TextView noticeView = viewInflated.findViewById(R.id.areaManagementNoticeUserInput);

newbuilder.setPositiveButton("Bestätigen", new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {

taskList.get(i).setNotice(noticeView.getText().toString());
notice.setText(taskList.get(i).getNotice());
dialog.dismiss();
}
});

newbuilder.setNegativeButton("Abbrechen", new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
dialog.cancel();
}
});

newbuilder.show();
}});

deleteArea.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
final AlertDialog.Builder newbuilder = new AlertDialog.Builder(v.getRootView().getContext());

newbuilder.setTitle("Das Grundstück wirklich löschen?");

newbuilder.setPositiveButton("Bestätigen", new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {

taskList.get(i).deleteFromExternalStorage(context);
taskList.remove(i);

notifyDataSetChanged();

if (BuildConfig.DEBUG)
{
for (OwnTask task: taskList)
{
Log.d(TAG, "areaList item: " + task.toString());
}
}

dialog.dismiss();
}
});

newbuilder.setNegativeButton("Abbrechen", new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
dialog.cancel();
}
});

newbuilder.show();
}});

builder.setPositiveButton("Bestätigen", new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {

if (taskList.size()-1 > i && taskList.get(i) != null)
{
taskList.get(i).deleteFromExternalStorage(context);
taskList.get(i).saveImageToExternalStorage(context);
}

if (BuildConfig.DEBUG)
{
for (OwnTask task: taskList)
{
Log.d(TAG, "areaList item: " + task.toString());
}
}

dialog.dismiss();
}
});

builder.setNegativeButton("Abbrechen", new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
dialog.cancel();
}
});

builder.show();
}
});

icon.setOnClickListener(new View.OnClickListener() { icon.setOnClickListener(new View.OnClickListener() {
@Override @Override
public void onClick(View v) public void onClick(View v)
final ConstraintLayout imageViewLayout = viewInflated.findViewById(R.id.taskLargeImageLayout); final ConstraintLayout imageViewLayout = viewInflated.findViewById(R.id.taskLargeImageLayout);
final ImageView imageView = viewInflated.findViewById(R.id.taskLargeImage); final ImageView imageView = viewInflated.findViewById(R.id.taskLargeImage);


//ConstraintLayout.LayoutParams layoutParams = new ConstraintLayout.LayoutParams(taskList.get(i).getImage().getWidth(),5 * taskList.get(i).getImage().getHeight());
//imageViewLayout.setLayoutParams(layoutParams);
Log.d("TaskAdapter", String.valueOf(taskList.get(i).getImage().getHeight()));

//ConstraintLayout.LayoutParams layoutParams = new ConstraintLayout.LayoutParams(taskList.get(i).getImage().getWidth(), taskList.get(i).getImage().getHeight());
//layoutParams.width = taskList.get(i).getImage().getWidth();
//layoutParams.height = taskList.get(i).getImage().getHeight();
//imageView.setLayoutParams(layoutParams);
imageView.setImageBitmap(taskList.get(i).getImage()); imageView.setImageBitmap(taskList.get(i).getImage());


builder.setNegativeButton("Zurück", new DialogInterface.OnClickListener() { builder.setNegativeButton("Zurück", new DialogInterface.OnClickListener() {

+ 33
- 44
Code Android/meinWald/app/src/main/java/com/example/meinwald/ui/task/TasksFragment.java View File

import android.content.DialogInterface; import android.content.DialogInterface;
import android.content.Intent; import android.content.Intent;
import android.content.pm.PackageManager; import android.content.pm.PackageManager;
import android.database.DataSetObserver;
import android.graphics.Bitmap; import android.graphics.Bitmap;
import android.graphics.BitmapFactory; import android.graphics.BitmapFactory;
import android.graphics.Color; import android.graphics.Color;


import com.example.meinwald.BuildConfig; import com.example.meinwald.BuildConfig;
import com.example.meinwald.R; import com.example.meinwald.R;
import com.example.meinwald.ui.area.AreaReference;
import com.example.meinwald.ui.area.OwnArea;
import com.google.android.gms.location.FusedLocationProviderClient; import com.google.android.gms.location.FusedLocationProviderClient;
import com.google.android.gms.location.LocationServices; import com.google.android.gms.location.LocationServices;
import com.google.android.gms.maps.CameraUpdateFactory; import com.google.android.gms.maps.CameraUpdateFactory;


//save and display location //save and display location
newTask.setLocation(mLastKnownLocation); newTask.setLocation(mLastKnownLocation);
locationText.setText("Lat: " +String.valueOf(mLastKnownLocation.getLatitude()) + " Lng: " + String.valueOf(mLastKnownLocation.getLongitude()));
locationText.setText("Auf " + newTask.getLocation().getAccuracy() + " Meter genau!");
} }
}); });


//save user input //save user input
newTask.setTitle(String.valueOf(titleView.getText())); newTask.setTitle(String.valueOf(titleView.getText()));
newTask.setNotice(String.valueOf(noticeView.getText())); newTask.setNotice(String.valueOf(noticeView.getText()));
newTask.setPathImage(newTask.saveImageToExternalStorage(getContext()));


boolean result = allTasks.add(newTask); boolean result = allTasks.add(newTask);


{ {
Log.d(TAG, "new Task: " + newTask.toString()); Log.d(TAG, "new Task: " + newTask.toString());
Log.d(TAG, "add new task result: " + result); Log.d(TAG, "add new task result: " + result);

/**
for (OwnTask task: allTasks)
{
if (BuildConfig.DEBUG) {
Log.d(TAG, task.toString());
}
}
**/
} }


instantiateTaskList(); instantiateTaskList();
{ {


//save image to external storage and save path //save image to external storage and save path
String path = saveReceivedImage(task.getImage(), task.getId());
String path = task.saveImageToExternalStorage(getContext());
task.setPathImage(path); task.setPathImage(path);


if (BuildConfig.DEBUG) { if (BuildConfig.DEBUG) {
} }
} }


private String saveReceivedImage(Bitmap bitmap, String imageName){

File path = null;

try {
path = new File(getContext().getFilesDir(), "meinWald" + File.separator + "Images");
if(!path.exists()){
path.mkdirs();
}

if (BuildConfig.DEBUG) {
Log.d(TAG, "Image file path: " + path);
}

File outFile = new File(path, imageName + ".jpeg");
if (!outFile.exists())
{
FileOutputStream outputStream = new FileOutputStream(outFile);
bitmap.compress(Bitmap.CompressFormat.JPEG, 100, outputStream);
outputStream.close();
}

} catch (FileNotFoundException e) {
Log.e(TAG, "Saving received message failed with", e);
} catch (IOException e) {
Log.e(TAG, "Saving received message failed with", e);
}

return path.toString();
}

/** /**
* Reads tasks saved in preferences as jsonStrings * Reads tasks saved in preferences as jsonStrings
* *
public void instantiateTaskList() public void instantiateTaskList()
{ {
final TaskAdapter adapter = new TaskAdapter(getActivity().getApplicationContext(),allTasks); final TaskAdapter adapter = new TaskAdapter(getActivity().getApplicationContext(),allTasks);

adapter.registerDataSetObserver(new DataSetObserver() {
@Override
public void onChanged() {
super.onChanged();

if (BuildConfig.DEBUG)
{
Log.d(TAG, "onChanged");
}

if (BuildConfig.DEBUG)
{
Log.d(TAG, "dataset size: " + taskList.getAdapter().getCount());
}

if (taskList.getAdapter().getCount() > 0)
{
allTasks = new ArrayList<>();

for (int i = 0; i < taskList.getAdapter().getCount(); i++)
{
allTasks.add((OwnTask) taskList.getAdapter().getItem(i));
}
}
}
});
taskList.setAdapter(adapter); taskList.setAdapter(adapter);


//initialise onClickListeners //initialise onClickListeners
{ {
Bitmap photo = (Bitmap) data.getExtras().get("data"); Bitmap photo = (Bitmap) data.getExtras().get("data");
newTask.setImage(photo); newTask.setImage(photo);
newTask.setPathImage(saveReceivedImage(photo,newTask.getId()));


if (imageToAdd != null && photo != null) if (imageToAdd != null && photo != null)
{ {

+ 43
- 4
Code Android/meinWald/app/src/main/res/layout/area_element.xml View File

android:focusable="false" android:focusable="false"
android:textColor="@android:color/primary_text_light" android:textColor="@android:color/primary_text_light"
android:textSize="22sp" android:textSize="22sp"
android:textStyle="bold"
app:layout_constraintStart_toStartOf="parent" app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" /> app:layout_constraintTop_toTopOf="parent" />


<TextView <TextView
android:id="@+id/areaInfoNotice" android:id="@+id/areaInfoNotice"
android:layout_width="0dp" android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_height="0dp"
android:layout_gravity="left" android:layout_gravity="left"
android:clickable="false" android:clickable="false"
android:duplicateParentState="true"
android:focusable="false" android:focusable="false"
android:focusableInTouchMode="false" android:focusableInTouchMode="false"
android:textColor="@android:color/primary_text_light" android:textColor="@android:color/primary_text_light"
android:textSize="12sp" android:textSize="12sp"
android:visibility="visible" android:visibility="visible"
app:layout_constraintEnd_toStartOf="@+id/taskIcon"
app:layout_constraintBottom_toTopOf="@+id/areaInfoArea"
app:layout_constraintEnd_toStartOf="@+id/areaIcon"
app:layout_constraintStart_toStartOf="parent" app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"
android:duplicateParentState="true"/>
app:layout_constraintTop_toTopOf="parent" />

<TextView
android:id="@+id/areaInfoAreatv"
android:layout_width="0dp"
android:layout_height="20dp"
android:layout_gravity="left"
android:layout_marginBottom="5dp"
android:clickable="false"
android:duplicateParentState="true"
android:focusable="false"
android:focusableInTouchMode="false"
android:text="Fläche:"
android:textColor="@android:color/primary_text_light"
android:textSize="14sp"
android:visibility="visible"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintStart_toStartOf="parent" />

<TextView
android:id="@+id/areaInfoArea"
android:layout_width="0dp"
android:layout_height="0dp"
android:layout_gravity="left"
android:layout_marginStart="5dp"
android:layout_marginLeft="5dp"
android:layout_marginBottom="5dp"
android:clickable="false"
android:duplicateParentState="true"
android:focusable="false"
android:focusableInTouchMode="false"
android:textColor="@android:color/primary_text_light"
android:textSize="14sp"
android:visibility="visible"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toStartOf="@+id/areaIcon"
app:layout_constraintStart_toEndOf="@+id/areaInfoAreatv"
app:layout_constraintTop_toTopOf="@+id/areaInfoAreatv" />


</androidx.constraintlayout.widget.ConstraintLayout> </androidx.constraintlayout.widget.ConstraintLayout>



+ 66
- 9
Code Android/meinWald/app/src/main/res/layout/area_input.xml View File

<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto" xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/layout_area_root" android:id="@+id/layout_area_root"
android:layout_width="fill_parent" android:layout_width="fill_parent"
android:layout_height="fill_parent" android:layout_height="fill_parent"
android:id="@+id/areaTitle" android:id="@+id/areaTitle"
android:layout_width="wrap_content" android:layout_width="wrap_content"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:layout_marginStart="5dp"
android:layout_marginLeft="5dp"
android:layout_marginTop="5dp"
android:text="Grundstück" android:text="Grundstück"
android:textAppearance="?android:attr/textAppearanceLarge" />
android:textAppearance="?android:attr/textAppearanceLarge"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" />


<EditText <EditText
android:id="@+id/areaTitleUserInput" android:id="@+id/areaTitleUserInput"
android:layout_width="match_parent" android:layout_width="match_parent"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:hint="Titel eingeben!">
android:layout_marginStart="5dp"
android:layout_marginLeft="5dp"
android:layout_marginEnd="5dp"
android:layout_marginRight="5dp"
android:hint="Titel eingeben!"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@+id/areaTitle">


<requestFocus /> <requestFocus />


android:id="@+id/areaManagementNotice" android:id="@+id/areaManagementNotice"
android:layout_width="wrap_content" android:layout_width="wrap_content"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:layout_marginStart="5dp"
android:layout_marginLeft="5dp"
android:layout_marginTop="15dp"
android:text="Beschreibung" android:text="Beschreibung"
android:textAppearance="?android:attr/textAppearanceLarge" />
android:textAppearance="?android:attr/textAppearanceLarge"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@+id/areaTitleUserInput" />


<EditText <EditText
android:id="@+id/areaManagementNoticeUserInput" android:id="@+id/areaManagementNoticeUserInput"
android:layout_width="match_parent" android:layout_width="match_parent"
android:layout_height="150dp" android:layout_height="150dp"
android:layout_marginStart="5dp"
android:layout_marginLeft="5dp"
android:layout_marginEnd="5dp"
android:layout_marginRight="5dp"
android:cursorVisible="true"
android:hint="Beschreibung eingeben!" android:hint="Beschreibung eingeben!"
android:isScrollContainer="true">
<requestFocus />
android:isScrollContainer="true"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@+id/areaManagementNotice">

</EditText> </EditText>


<Button <Button
android:id="@+id/areaStartTracking" android:id="@+id/areaStartTracking"
android:layout_width="match_parent" android:layout_width="match_parent"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:text="Grundstücksaufnahme Starten!" />
android:layout_marginStart="5dp"
android:layout_marginLeft="5dp"
android:layout_marginTop="15dp"
android:layout_marginEnd="5dp"
android:layout_marginRight="5dp"
android:text="Grundstücksaufnahme Starten!"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@+id/areaManagementNoticeUserInput" />

<Button <Button
android:id="@+id/areaStopTracking" android:id="@+id/areaStopTracking"
android:layout_width="match_parent" android:layout_width="match_parent"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:layout_marginStart="5dp"
android:layout_marginLeft="5dp"
android:layout_marginTop="15dp"
android:layout_marginEnd="5dp"
android:layout_marginRight="5dp"
android:text="Grundstücksaufnahme Beenden!" android:text="Grundstücksaufnahme Beenden!"
android:visibility="invisible"/>
android:visibility="invisible"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@+id/areaManagementNoticeUserInput" />

<Button
android:id="@+id/areaAddGPSPoint"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_marginStart="5dp"
android:layout_marginLeft="5dp"
android:layout_marginTop="5dp"
android:layout_marginEnd="5dp"
android:layout_marginRight="5dp"
android:text="Grenzpunkt hinzufügen"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@+id/areaStartTracking" />


</LinearLayout>
</androidx.constraintlayout.widget.ConstraintLayout>

+ 40
- 5
Code Android/meinWald/app/src/main/res/layout/area_management.xml View File

android:layout_marginStart="5dp" android:layout_marginStart="5dp"
android:layout_marginLeft="5dp" android:layout_marginLeft="5dp"
android:layout_marginTop="15dp" android:layout_marginTop="15dp"
android:text="Bild"
android:text="Zuletzt überprüft"
android:textSize="18sp" android:textSize="18sp"
android:textStyle="bold" android:textStyle="bold"
app:layout_constraintStart_toStartOf="parent" app:layout_constraintStart_toStartOf="parent"
app:layout_constraintStart_toStartOf="parent" app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@+id/textView4" /> app:layout_constraintTop_toBottomOf="@+id/textView4" />


<TextView
android:id="@+id/textView7"
android:layout_width="250dp"
android:layout_height="wrap_content"
android:layout_marginStart="5dp"
android:layout_marginLeft="5dp"
android:layout_marginTop="15dp"
android:text="Bild"
android:textSize="18sp"
android:textStyle="bold"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@+id/areaManagementLastChecked" />

<TextView
android:id="@+id/areaManagementLastChecked"
android:layout_width="0dp"
android:layout_height="30dp"
android:layout_marginStart="5dp"
android:layout_marginLeft="5dp"
android:textSize="12sp"
app:layout_constraintEnd_toStartOf="@+id/areaManageNewDate"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@+id/textView6" />

<ImageView <ImageView
android:id="@+id/areaManageImage" android:id="@+id/areaManageImage"
android:layout_width="match_parent" android:layout_width="match_parent"
android:layout_marginLeft="5dp" android:layout_marginLeft="5dp"
android:layout_marginEnd="5dp" android:layout_marginEnd="5dp"
android:layout_marginRight="5dp" android:layout_marginRight="5dp"
android:src="@android:drawable/ic_menu_gallery"
android:visibility="visible"
app:layout_constraintEnd_toEndOf="parent" app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintHorizontal_bias="1.0"
app:layout_constraintStart_toStartOf="parent" app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@+id/textView6"
android:src="@android:drawable/ic_menu_gallery"
android:visibility="visible"/>
app:layout_constraintTop_toBottomOf="@+id/textView7" />


<ImageView <ImageView
android:id="@+id/areaManageNewDescription" android:id="@+id/areaManageNewDescription"
app:layout_constraintEnd_toEndOf="@+id/areaManageGPSPoints" app:layout_constraintEnd_toEndOf="@+id/areaManageGPSPoints"
android:src="@android:drawable/ic_popup_sync" /> android:src="@android:drawable/ic_popup_sync" />


<ImageView
android:id="@+id/areaManageNewDate"
android:layout_width="30dp"
android:layout_height="30dp"
android:src="@android:drawable/ic_popup_sync"
android:visibility="visible"
app:layout_constraintBottom_toBottomOf="@+id/areaManagementLastChecked"
app:layout_constraintEnd_toEndOf="@+id/areaManageGPSPoints"
app:tint="#1B5E20" />

<ImageView <ImageView
android:id="@+id/areaManageNewImage" android:id="@+id/areaManageNewImage"
android:layout_width="30dp" android:layout_width="30dp"
android:visibility="visible" android:visibility="visible"
app:layout_constraintEnd_toEndOf="parent" app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintTop_toTopOf="parent" app:layout_constraintTop_toTopOf="parent"
/>
/>
</androidx.constraintlayout.widget.ConstraintLayout> </androidx.constraintlayout.widget.ConstraintLayout>

+ 7
- 2
Code Android/meinWald/app/src/main/res/layout/image_large.xml View File



<ImageView <ImageView
android:id="@+id/taskLargeImage" android:id="@+id/taskLargeImage"
android:layout_width="match_parent"
android:layout_height="575dp"
android:layout_width="0dp"
android:layout_height="500dp"
android:layout_marginStart="40dp"
android:layout_marginLeft="40dp"
android:layout_marginTop="60dp"
android:layout_marginEnd="40dp"
android:layout_marginRight="40dp"
android:scaleType="fitXY" android:scaleType="fitXY"
app:layout_constraintBottom_toBottomOf="parent" app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent" app:layout_constraintEnd_toEndOf="parent"

+ 22
- 6
Code Android/meinWald/app/src/main/res/layout/task_element.xml View File



<TextView <TextView
android:id="@+id/taskInfoTitle" android:id="@+id/taskInfoTitle"
android:layout_width="match_parent"
android:layout_height="30dp"
android:layout_width="0dp"
android:layout_height="32dp"
android:layout_gravity="left" android:layout_gravity="left"
android:layout_marginStart="5dp" android:layout_marginStart="5dp"
android:layout_marginLeft="5dp" android:layout_marginLeft="5dp"
android:layout_marginTop="5dp" android:layout_marginTop="5dp"
android:layout_marginEnd="5dp"
android:layout_marginRight="5dp"
android:clickable="false" android:clickable="false"
android:focusable="false" android:focusable="false"

android:textColor="@android:color/primary_text_light" android:textColor="@android:color/primary_text_light"
android:textSize="22sp" android:textSize="22sp"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintEnd_toStartOf="@+id/taskManageTask"
app:layout_constraintStart_toStartOf="parent" app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" /> app:layout_constraintTop_toTopOf="parent" />


<ImageView
android:id="@+id/taskManageTask"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_marginTop="5dp"
android:layout_marginEnd="5dp"
android:layout_marginRight="5dp"
android:clickable="true"
android:duplicateParentState="true"
android:focusable="false"
android:focusableInTouchMode="false"
android:src="@android:drawable/ic_menu_manage"
android:visibility="visible"
app:layout_constraintBottom_toTopOf="@+id/areaInfoView"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintHorizontal_bias="0.0"
app:layout_constraintStart_toEndOf="@+id/areaInfoTitle"
app:layout_constraintTop_toTopOf="parent" />

<androidx.constraintlayout.widget.ConstraintLayout <androidx.constraintlayout.widget.ConstraintLayout
android:id="@+id/taskInfoView" android:id="@+id/taskInfoView"
android:layout_width="0dp" android:layout_width="0dp"

+ 0
- 2
Code Android/meinWald/app/src/main/res/layout/task_input.xml View File

android:hint="Beschreibung eingeben!" android:hint="Beschreibung eingeben!"
android:isScrollContainer="true"> android:isScrollContainer="true">


<requestFocus />

</EditText> </EditText>


<Button <Button

+ 144
- 0
Code Android/meinWald/app/src/main/res/layout/task_management.xml View File

<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
xmlns:app="http://schemas.android.com/apk/res-auto">

<TextView
android:id="@+id/taskManageTitle"
android:layout_width="wrap_content"
android:layout_height="50dp"
android:layout_marginStart="5dp"
android:layout_marginLeft="5dp"
android:layout_marginTop="5dp"
android:text="TextView"
android:textSize="36sp"
android:textStyle="bold"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" />

<TextView
android:id="@+id/textView2"
android:layout_width="250dp"
android:layout_height="wrap_content"
android:layout_marginStart="5dp"
android:layout_marginLeft="5dp"
android:layout_marginTop="5dp"
android:text="Beschreibung"
android:textSize="18sp"
android:textStyle="bold"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@+id/taskManageTitle" />

<TextView
android:id="@+id/taskManageNotice"
android:layout_width="0dp"
android:layout_height="75dp"
android:layout_marginStart="5dp"
android:layout_marginLeft="5dp"
android:layout_marginEnd="5dp"
android:layout_marginRight="5dp"
android:isScrollContainer="true"
android:textSize="12sp"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@+id/textView2" />

<TextView
android:id="@+id/textView4"
android:layout_width="250dp"
android:layout_height="wrap_content"
android:layout_marginStart="5dp"
android:layout_marginLeft="5dp"
android:layout_marginTop="15dp"
android:text="Standort"
android:textSize="18sp"
android:textStyle="bold"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@+id/taskManageNotice" />

<TextView
android:id="@+id/textView6"
android:layout_width="250dp"
android:layout_height="wrap_content"
android:layout_marginStart="5dp"
android:layout_marginLeft="5dp"
android:layout_marginTop="15dp"
android:text="Bild"
android:textSize="18sp"
android:textStyle="bold"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@+id/taskManageGPSPoint" />

<TextView
android:id="@+id/taskManageGPSPoint"
android:layout_width="match_parent"
android:layout_height="30dp"
android:layout_marginStart="5dp"
android:layout_marginLeft="5dp"
android:layout_marginEnd="5dp"
android:layout_marginRight="5dp"
android:textSize="12sp"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@+id/textView4" />

<ImageView
android:id="@+id/taskManageImage"
android:layout_width="match_parent"
android:layout_height="200dp"
android:layout_marginStart="5dp"
android:layout_marginLeft="5dp"
android:layout_marginEnd="5dp"
android:layout_marginRight="5dp"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@+id/textView6"
android:src="@android:drawable/ic_menu_gallery"
android:visibility="visible"/>

<ImageView
android:id="@+id/taskManageNewDescription"
android:layout_width="30dp"
android:layout_height="30dp"
app:tint="#1B5E20"
android:visibility="visible"
app:layout_constraintBottom_toBottomOf="@+id/taskManageNotice"
app:layout_constraintEnd_toEndOf="@+id/taskManageNotice"
android:src="@android:drawable/ic_popup_sync" />

<ImageView
android:id="@+id/taskManageNewGPS"
android:layout_width="30dp"
android:layout_height="30dp"
app:tint="#1B5E20"
android:visibility="visible"
app:layout_constraintBottom_toBottomOf="@+id/taskManageGPSPoint"
app:layout_constraintEnd_toEndOf="@+id/taskManageGPSPoint"
android:src="@android:drawable/ic_popup_sync" />

<ImageView
android:id="@+id/taskManageNewImage"
android:layout_width="30dp"
android:layout_height="30dp"
app:tint="#1B5E20"
android:visibility="visible"
app:layout_constraintBottom_toBottomOf="@+id/taskManageImage"
app:layout_constraintEnd_toEndOf="@+id/taskManageImage"
android:src="@android:drawable/ic_menu_camera" />

<ImageView
android:id="@+id/taskManageDeleteTask"
android:layout_width="50dp"
android:layout_height="50dp"
android:layout_marginTop="5dp"
android:layout_marginEnd="5dp"
android:layout_marginRight="5dp"
android:src="@android:drawable/ic_menu_delete"
app:tint="#B71C1C"
android:visibility="visible"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintTop_toTopOf="parent"
/>

</androidx.constraintlayout.widget.ConstraintLayout>

+ 6
- 1
Code Android/meinWald/app/src/main/res/values/colors.xml View File

<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<resources> <resources>
<color name="colorPrimary">#1B5E20</color> <color name="colorPrimary">#1B5E20</color>
<color name="colorPrimaryDark">#3700B3</color>
<color name="colorPrimaryDark">#1B5E20</color>
<color name="colorAccent">#03DAC5</color> <color name="colorAccent">#03DAC5</color>
<color name="selectionBackground">#c0edc3</color> <color name="selectionBackground">#c0edc3</color>
<color name="colorArea1">#57a639</color>
<color name="colorArea2">#819b45</color>
<color name="colorArea3">#d3d30c</color>
<color name="colorArea4">#df9600</color>
<color name="colorArea5">#df3d00</color>
</resources> </resources>

Loading…
Cancel
Save