mirror of
https://codeberg.org/Freeyourgadget/Gadgetbridge
synced 2024-09-27 00:38:01 +02:00
Add chart to each item in Activity list
This commit is contained in:
parent
17c208aa44
commit
01e99d2809
@ -17,11 +17,14 @@
|
|||||||
along with this program. If not, see <http://www.gnu.org/licenses/>. */
|
along with this program. If not, see <http://www.gnu.org/licenses/>. */
|
||||||
package nodomain.freeyourgadget.gadgetbridge.activities;
|
package nodomain.freeyourgadget.gadgetbridge.activities;
|
||||||
|
|
||||||
|
import android.content.Context;
|
||||||
import android.os.Bundle;
|
import android.os.Bundle;
|
||||||
import android.view.LayoutInflater;
|
import android.view.LayoutInflater;
|
||||||
import android.view.View;
|
import android.view.View;
|
||||||
import android.view.ViewGroup;
|
import android.view.ViewGroup;
|
||||||
|
|
||||||
|
import androidx.annotation.Nullable;
|
||||||
|
|
||||||
import com.github.mikephil.charting.charts.Chart;
|
import com.github.mikephil.charting.charts.Chart;
|
||||||
import com.github.mikephil.charting.charts.LineChart;
|
import com.github.mikephil.charting.charts.LineChart;
|
||||||
import com.github.mikephil.charting.components.Legend;
|
import com.github.mikephil.charting.components.Legend;
|
||||||
@ -37,11 +40,11 @@ import org.slf4j.LoggerFactory;
|
|||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
import nodomain.freeyourgadget.gadgetbridge.GBApplication;
|
|
||||||
import nodomain.freeyourgadget.gadgetbridge.R;
|
import nodomain.freeyourgadget.gadgetbridge.R;
|
||||||
import nodomain.freeyourgadget.gadgetbridge.activities.charts.AbstractChartFragment;
|
import nodomain.freeyourgadget.gadgetbridge.activities.charts.AbstractChartFragment;
|
||||||
import nodomain.freeyourgadget.gadgetbridge.activities.charts.ChartsData;
|
import nodomain.freeyourgadget.gadgetbridge.activities.charts.ChartsData;
|
||||||
import nodomain.freeyourgadget.gadgetbridge.activities.charts.ChartsHost;
|
import nodomain.freeyourgadget.gadgetbridge.activities.charts.ChartsHost;
|
||||||
|
import nodomain.freeyourgadget.gadgetbridge.database.DBAccess;
|
||||||
import nodomain.freeyourgadget.gadgetbridge.database.DBHandler;
|
import nodomain.freeyourgadget.gadgetbridge.database.DBHandler;
|
||||||
import nodomain.freeyourgadget.gadgetbridge.impl.GBDevice;
|
import nodomain.freeyourgadget.gadgetbridge.impl.GBDevice;
|
||||||
import nodomain.freeyourgadget.gadgetbridge.model.ActivitySample;
|
import nodomain.freeyourgadget.gadgetbridge.model.ActivitySample;
|
||||||
@ -54,63 +57,41 @@ public class ActivitySummariesChartFragment extends AbstractChartFragment {
|
|||||||
private int startTime;
|
private int startTime;
|
||||||
private int endTime;
|
private int endTime;
|
||||||
private GBDevice gbDevice;
|
private GBDevice gbDevice;
|
||||||
|
private View view;
|
||||||
|
|
||||||
public void setDateAndGetData(GBDevice gbDevice, long startTime, long endTime) {
|
public void setDateAndGetData(GBDevice gbDevice, long startTime, long endTime) {
|
||||||
this.startTime = (int) startTime;
|
this.startTime = (int) startTime;
|
||||||
this.endTime = (int) endTime;
|
this.endTime = (int) endTime;
|
||||||
this.gbDevice = gbDevice;
|
this.gbDevice = gbDevice;
|
||||||
try {
|
if (this.view != null) {
|
||||||
populate_charts_data();
|
createLocalRefreshTask("Visualizing data", getActivity()).execute();
|
||||||
} catch (Exception e) {
|
|
||||||
LOG.debug("Unable to fill charts data right now:", e);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
protected RefreshTask createLocalRefreshTask(String task, Context context) {
|
||||||
|
return new RefreshTask(task, context);
|
||||||
private void populate_charts_data() {
|
|
||||||
int LEGEND_TEXT_COLOR = 0;
|
|
||||||
|
|
||||||
try (DBHandler handler = GBApplication.acquireDB()) {
|
|
||||||
try {
|
|
||||||
LEGEND_TEXT_COLOR = GBApplication.getTextColor(getContext());
|
|
||||||
} catch (Exception e) {
|
|
||||||
LOG.debug("Unable to get color right now:", e);
|
|
||||||
}
|
|
||||||
|
|
||||||
List<? extends ActivitySample> samples = getSamples(handler, gbDevice, startTime, endTime);
|
|
||||||
DefaultChartsData dcd=null;
|
|
||||||
try {
|
|
||||||
dcd = refresh(gbDevice, samples);
|
|
||||||
}catch(Exception e){
|
|
||||||
LOG.debug("Unable to get charts data right now:", e);
|
|
||||||
}
|
|
||||||
if (dcd != null) {
|
|
||||||
mChart.getLegend().setTextColor(LEGEND_TEXT_COLOR);
|
|
||||||
mChart.setData(null); // workaround for https://github.com/PhilJay/MPAndroidChart/issues/2317
|
|
||||||
mChart.getXAxis().setValueFormatter(dcd.getXValueFormatter());
|
|
||||||
mChart.setData((LineData) dcd.getData());
|
|
||||||
mChart.invalidate();
|
|
||||||
}
|
|
||||||
} catch (Exception e) {
|
|
||||||
LOG.error("Unable to get charts data:", e);
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public View onCreateView(LayoutInflater inflater, ViewGroup container,
|
public View onCreateView(LayoutInflater inflater, ViewGroup container,
|
||||||
Bundle savedInstanceState) {
|
Bundle savedInstanceState) {
|
||||||
init();
|
|
||||||
View rootView = inflater.inflate(R.layout.fragment_charts, container, false);
|
View rootView = inflater.inflate(R.layout.fragment_charts, container, false);
|
||||||
mChart = rootView.findViewById(R.id.activitysleepchart);
|
mChart = rootView.findViewById(R.id.activitysleepchart);
|
||||||
if (this.gbDevice != null) {
|
|
||||||
setupChart();
|
|
||||||
populate_charts_data();
|
|
||||||
}
|
|
||||||
return rootView;
|
return rootView;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void onViewCreated(final View view, @Nullable Bundle savedInstanceState) {
|
||||||
|
super.onViewCreated(view, savedInstanceState);
|
||||||
|
init();
|
||||||
|
this.view = view;
|
||||||
|
if (this.gbDevice != null) {
|
||||||
|
setupChart();
|
||||||
|
createLocalRefreshTask("Visualizing data", getActivity()).execute();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String getTitle() {
|
public String getTitle() {
|
||||||
return "";
|
return "";
|
||||||
@ -194,4 +175,32 @@ public class ActivitySummariesChartFragment extends AbstractChartFragment {
|
|||||||
protected void updateChartsnUIThread(ChartsData chartsData) {
|
protected void updateChartsnUIThread(ChartsData chartsData) {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public class RefreshTask extends DBAccess {
|
||||||
|
|
||||||
|
public RefreshTask(String task, Context context) {
|
||||||
|
super(task, context);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected void doInBackground(DBHandler handler) {
|
||||||
|
List<? extends ActivitySample> samples = getAllSamples(handler, gbDevice, startTime, endTime);
|
||||||
|
|
||||||
|
DefaultChartsData dcd = null;
|
||||||
|
try {
|
||||||
|
dcd = refresh(gbDevice, samples);
|
||||||
|
} catch (Exception e) {
|
||||||
|
LOG.debug("Unable to get charts data right now:", e);
|
||||||
|
}
|
||||||
|
if (dcd != null) {
|
||||||
|
mChart.setData(null); // workaround for https://github.com/PhilJay/MPAndroidChart/issues/2317
|
||||||
|
mChart.getXAxis().setValueFormatter(dcd.getXValueFormatter());
|
||||||
|
mChart.setData((LineData) dcd.getData());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected void onPostExecute(Object o) {
|
||||||
|
mChart.invalidate();
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
@ -24,6 +24,7 @@ import android.os.Bundle;
|
|||||||
import android.view.LayoutInflater;
|
import android.view.LayoutInflater;
|
||||||
import android.view.View;
|
import android.view.View;
|
||||||
import android.view.ViewGroup;
|
import android.view.ViewGroup;
|
||||||
|
import android.widget.AdapterView;
|
||||||
import android.widget.ListView;
|
import android.widget.ListView;
|
||||||
import android.widget.TextView;
|
import android.widget.TextView;
|
||||||
|
|
||||||
@ -64,6 +65,19 @@ public class ActivityListingChartFragment extends AbstractChartFragment {
|
|||||||
ListView stepsList = rootView.findViewById(R.id.itemListView);
|
ListView stepsList = rootView.findViewById(R.id.itemListView);
|
||||||
stepListAdapter = new ActivityListingAdapter(getContext());
|
stepListAdapter = new ActivityListingAdapter(getContext());
|
||||||
stepsList.setAdapter(stepListAdapter);
|
stepsList.setAdapter(stepListAdapter);
|
||||||
|
|
||||||
|
stepsList.setOnItemClickListener(new AdapterView.OnItemClickListener() {
|
||||||
|
@Override
|
||||||
|
public void onItemClick(AdapterView<?> adapterView, View view, int i, long l) {
|
||||||
|
ActivitySession item = stepListAdapter.getItem(i);
|
||||||
|
if (item.getSessionType() != ActivitySession.SESSION_SUMMARY) {
|
||||||
|
int tsFrom = (int) (item.getStartTime().getTime() / 1000);
|
||||||
|
int tsTo = (int) (item.getEndTime().getTime() / 1000);
|
||||||
|
showDetail(tsFrom, tsTo, getChartsHost().getDevice());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
stepsDateView = rootView.findViewById(R.id.stepsDateView);
|
stepsDateView = rootView.findViewById(R.id.stepsDateView);
|
||||||
FloatingActionButton fab;
|
FloatingActionButton fab;
|
||||||
fab = rootView.findViewById(R.id.fab);
|
fab = rootView.findViewById(R.id.fab);
|
||||||
@ -169,7 +183,6 @@ public class ActivityListingChartFragment extends AbstractChartFragment {
|
|||||||
String activityName = stepListAdapter.getActivityName(ongoingSession);
|
String activityName = stepListAdapter.getActivityName(ongoingSession);
|
||||||
int icon = stepListAdapter.getIcon(ongoingSession);
|
int icon = stepListAdapter.getIcon(ongoingSession);
|
||||||
|
|
||||||
|
|
||||||
String text = String.format("%s:\u00A0%s, %s:\u00A0%s, %s:\u00A0%s, %s:\u00A0%s", activityName, durationLabel, getString(R.string.heart_rate), hrLabel, getString(R.string.steps), stepLabel, getString(R.string.distance), distanceLabel);
|
String text = String.format("%s:\u00A0%s, %s:\u00A0%s, %s:\u00A0%s, %s:\u00A0%s", activityName, durationLabel, getString(R.string.heart_rate), hrLabel, getString(R.string.steps), stepLabel, getString(R.string.distance), distanceLabel);
|
||||||
|
|
||||||
final Snackbar snackbar = Snackbar.make(rootView, text, 1000 * 8);
|
final Snackbar snackbar = Snackbar.make(rootView, text, 1000 * 8);
|
||||||
@ -181,7 +194,6 @@ public class ActivityListingChartFragment extends AbstractChartFragment {
|
|||||||
@Override
|
@Override
|
||||||
public void onClick(View view) {
|
public void onClick(View view) {
|
||||||
snackbar.dismiss();
|
snackbar.dismiss();
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
);
|
);
|
||||||
@ -189,11 +201,15 @@ public class ActivityListingChartFragment extends AbstractChartFragment {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private void showDashboard(int date, GBDevice device) {
|
private void showDashboard(int date, GBDevice device) {
|
||||||
|
|
||||||
FragmentManager fm = getActivity().getSupportFragmentManager();
|
FragmentManager fm = getActivity().getSupportFragmentManager();
|
||||||
ActivityListingDashboard editNameDialogFragment = ActivityListingDashboard.newInstance(date, device);
|
ActivityListingDashboard listingDashboardFragment = ActivityListingDashboard.newInstance(date, device);
|
||||||
editNameDialogFragment.show(fm, "activity_list_total_dashboard");
|
listingDashboardFragment.show(fm, "activity_list_total_dashboard");
|
||||||
|
}
|
||||||
|
|
||||||
|
private void showDetail(int tsFrom, int tsTo, GBDevice device) {
|
||||||
|
FragmentManager fm = getActivity().getSupportFragmentManager();
|
||||||
|
ActivityListingDetail listingDetailFragment = ActivityListingDetail.newInstance(tsFrom, tsTo, device);
|
||||||
|
listingDetailFragment.show(fm, "activity_list_detail");
|
||||||
}
|
}
|
||||||
|
|
||||||
private static class MyChartsData extends ChartsData {
|
private static class MyChartsData extends ChartsData {
|
||||||
@ -203,7 +219,6 @@ public class ActivityListingChartFragment extends AbstractChartFragment {
|
|||||||
MyChartsData(List<ActivitySession> stepSessions, ActivitySession ongoingSession) {
|
MyChartsData(List<ActivitySession> stepSessions, ActivitySession ongoingSession) {
|
||||||
this.stepSessions = stepSessions;
|
this.stepSessions = stepSessions;
|
||||||
this.ongoingSession = ongoingSession;
|
this.ongoingSession = ongoingSession;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public List<ActivitySession> getStepSessions() {
|
public List<ActivitySession> getStepSessions() {
|
||||||
@ -213,8 +228,5 @@ public class ActivityListingChartFragment extends AbstractChartFragment {
|
|||||||
public ActivitySession getOngoingSession() {
|
public ActivitySession getOngoingSession() {
|
||||||
return this.ongoingSession;
|
return this.ongoingSession;
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -0,0 +1,61 @@
|
|||||||
|
package nodomain.freeyourgadget.gadgetbridge.activities.charts;
|
||||||
|
|
||||||
|
import android.os.Bundle;
|
||||||
|
import android.view.LayoutInflater;
|
||||||
|
import android.view.View;
|
||||||
|
import android.view.ViewGroup;
|
||||||
|
|
||||||
|
import androidx.annotation.Nullable;
|
||||||
|
import androidx.fragment.app.DialogFragment;
|
||||||
|
|
||||||
|
import org.slf4j.Logger;
|
||||||
|
import org.slf4j.LoggerFactory;
|
||||||
|
|
||||||
|
import nodomain.freeyourgadget.gadgetbridge.R;
|
||||||
|
import nodomain.freeyourgadget.gadgetbridge.activities.ActivitySummariesChartFragment;
|
||||||
|
import nodomain.freeyourgadget.gadgetbridge.impl.GBDevice;
|
||||||
|
|
||||||
|
public class ActivityListingDetail extends DialogFragment {
|
||||||
|
protected static final Logger LOG = LoggerFactory.getLogger(ActivityListingDetail.class);
|
||||||
|
|
||||||
|
public ActivityListingDetail() {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
public static ActivityListingDetail newInstance(int tsFrom, int tsTo, GBDevice device) {
|
||||||
|
ActivityListingDetail frag = new ActivityListingDetail();
|
||||||
|
Bundle args = new Bundle();
|
||||||
|
args.putInt("tsFrom", tsFrom);
|
||||||
|
args.putInt("tsTo", tsTo);
|
||||||
|
args.putParcelable(GBDevice.EXTRA_DEVICE, device);
|
||||||
|
frag.setArguments(args);
|
||||||
|
return frag;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public View onCreateView(LayoutInflater inflater, ViewGroup container,
|
||||||
|
Bundle savedInstanceState) {
|
||||||
|
return inflater.inflate(R.layout.activity_list_detail, container);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void onViewCreated(final View view, @Nullable Bundle savedInstanceState) {
|
||||||
|
|
||||||
|
super.onViewCreated(view, savedInstanceState);
|
||||||
|
|
||||||
|
int tsFrom = getArguments().getInt("tsFrom");
|
||||||
|
int tsTo = getArguments().getInt("tsTo");
|
||||||
|
GBDevice gbDevice;
|
||||||
|
gbDevice = getArguments().getParcelable(GBDevice.EXTRA_DEVICE);
|
||||||
|
if (gbDevice == null) {
|
||||||
|
throw new IllegalArgumentException("Must provide a device when invoking this activity");
|
||||||
|
}
|
||||||
|
|
||||||
|
final ActivitySummariesChartFragment activitySummariesChartFragment = new ActivitySummariesChartFragment();
|
||||||
|
getChildFragmentManager()
|
||||||
|
.beginTransaction()
|
||||||
|
.replace(R.id.chartsFragmentHolder, activitySummariesChartFragment)
|
||||||
|
.commit();
|
||||||
|
activitySummariesChartFragment.setDateAndGetData(gbDevice, tsFrom, tsTo);
|
||||||
|
}
|
||||||
|
}
|
18
app/src/main/res/layout/activity_list_detail.xml
Normal file
18
app/src/main/res/layout/activity_list_detail.xml
Normal file
@ -0,0 +1,18 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
|
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||||
|
android:id="@+id/activity_battery_info_master_layout"
|
||||||
|
android:layout_width="match_parent"
|
||||||
|
android:layout_height="wrap_content"
|
||||||
|
android:layout_marginStart="0dp"
|
||||||
|
android:layout_marginTop="10dp"
|
||||||
|
android:layout_marginBottom="10dp"
|
||||||
|
android:gravity="center|center_vertical"
|
||||||
|
android:minWidth="1000dp"
|
||||||
|
android:orientation="vertical">
|
||||||
|
|
||||||
|
<FrameLayout
|
||||||
|
android:id="@+id/chartsFragmentHolder"
|
||||||
|
android:layout_width="match_parent"
|
||||||
|
android:layout_height="300dp"></FrameLayout>
|
||||||
|
|
||||||
|
</LinearLayout>
|
Loading…
Reference in New Issue
Block a user