/*
* Copyright (C) 2012 - 2014 jonas.oreland@gmail.com
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
package org.runnerup.workout;
import android.annotation.TargetApi;
import android.content.Context;
import android.content.SharedPreferences;
import android.content.res.Resources;
import android.os.Build;
import android.text.format.DateUtils;
import android.util.Log;
import android.util.Pair;
import org.runnerup.R;
import org.runnerup.common.util.Constants.DB;
import org.runnerup.util.Formatter;
import org.runnerup.util.HRZones;
import org.runnerup.util.SafeParse;
import org.runnerup.view.AudioCueSettingsActivity;
import org.runnerup.workout.Workout.StepListEntry;
import org.runnerup.workout.feedback.AudioCountdownFeedback;
import org.runnerup.workout.feedback.AudioFeedback;
import org.runnerup.workout.feedback.CoachFeedback;
import org.runnerup.workout.feedback.CountdownFeedback;
import org.runnerup.workout.feedback.HRMStateChangeFeedback;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
@TargetApi(Build.VERSION_CODES.FROYO)
public class WorkoutBuilder {
/**
* @return workout based on SharedPreferences
*/
public static Workout createDefaultWorkout(Resources res, SharedPreferences prefs,
Dimension target) {
Workout w = new Workout();
w.sport = prefs.getInt(res.getString(R.string.pref_basic_sport), DB.ACTIVITY.SPORT_RUNNING);
if (prefs.getBoolean(res.getString(R.string.pref_countdown_active), false))
{
long val = 0;
String vals = prefs.getString(res.getString(R.string.pref_countdown_time), "0");
try {
val = Long.parseLong(vals);
} catch (NumberFormatException e) {
}
if (val > 0) {
Step step = Step.createPauseStep(Dimension.TIME, val);
w.steps.add(step);
}
}
Step step = new Step();
if (prefs.getBoolean(res.getString(R.string.pref_autolap_active), false)) {
double val = 0;
String vals = prefs.getString(res.getString(R.string.pref_autolap), "1000");
try {
val = Double.parseDouble(vals);
} catch (NumberFormatException e) {
}
step.setAutolap(val);
}
addAutoPauseTrigger(res, step, prefs);
w.steps.add(step);
if (target == Dimension.PACE) {
double unitMeters = Formatter.getUnitMeters(res, prefs);
double seconds_per_unit = (double) SafeParse.parseSeconds(
prefs.getString(res.getString(R.string.pref_basic_target_pace_max), "00:05:00"), 5 * 60);
int targetPaceRange = prefs.getInt(res.getString(R.string.pref_basic_target_pace_min_range), 15);
double targetPaceMax = seconds_per_unit / unitMeters;
double targetPaceMin = (targetPaceMax * unitMeters - targetPaceRange) / unitMeters;
Range range = new Range(targetPaceMin, targetPaceMax);
step.targetType = Dimension.PACE;
step.targetValue = range;
} else if (target == Dimension.HRZ) {
HRZones hrCalc = new HRZones(res, prefs);
int zone = prefs.getInt(res.getString(R.string.pref_basic_target_hrz), -1);
if (zone >= 0) {
Pair<Integer, Integer> vals = hrCalc.getHRValues(zone + 1);
if (vals != null) {
step.targetType = Dimension.HR;
step.targetValue = new Range(vals.first, vals.second);
}
}
}
/**
*
*/
return w;
}
private static void addAutoPauseTrigger(Resources res, Step step, SharedPreferences prefs) {
boolean enableAutoPause = prefs.getBoolean(res.getString(R.string.pref_autopause_active), true);
if (!enableAutoPause)
return;
float autoPauseMinSpeed = 0;
float autoPauseAfterSeconds = 4f;
String val = prefs.getString(res.getString(R.string.pref_autopause_minpace), "60");
try {
float autoPauseMinPace = Float.parseFloat(val);
if (autoPauseMinPace > 0)
autoPauseMinSpeed = 1000 / (autoPauseMinPace * 60);
} catch (NumberFormatException e) {
}
val = prefs.getString(res.getString(R.string.pref_autopause_afterseconds), "4");
try {
autoPauseAfterSeconds = Float.parseFloat(val);
} catch (NumberFormatException e) {
}
AutoPauseTrigger tr = new AutoPauseTrigger(autoPauseAfterSeconds, autoPauseMinSpeed);
step.triggers.add(tr);
}
public static Workout createDefaultIntervalWorkout(Resources res, SharedPreferences prefs) {
Workout w = new Workout();
final boolean warmup = true;
final boolean cooldown = true;
final boolean convertRestToRecovery = prefs.getBoolean(res.getString(
R.string.pref_convert_interval_distance_rest_to_recovery), true);
if (warmup) {
Step step = new Step();
step.intensity = Intensity.WARMUP;
step.durationType = null;
addAutoPauseTrigger(res, step, prefs);
w.steps.add(step);
}
int repetitions = (int) SafeParse.parseDouble(prefs.getString(res.getString(R.string.pref_interval_repetitions), "1"),
1);
int intervalType = prefs.getInt(res.getString(R.string.pref_interval_type), 0);
long intervalTime = SafeParse.parseSeconds(prefs.getString(res.getString(R.string.pref_interval_time), "00:04:00"),
4 * 60);
double intevalDistance = SafeParse.parseDouble(prefs.getString(res.getString(R.string.pref_interval_distance), "1000"),
1000);
int intervalRestType = prefs.getInt(res.getString(R.string.pref_interval_rest_type), 0);
long intervalRestTime = SafeParse.parseSeconds(
prefs.getString(res.getString(R.string.pref_interval_rest_time), "00:01:00"), 60);
double intevalRestDistance = SafeParse.parseDouble(
prefs.getString(res.getString(R.string.pref_interval_rest_distance), "200"), 200);
RepeatStep repeat = new RepeatStep();
repeat.repeatCount = repetitions;
{
Step step = new Step();
switch (intervalType) {
case 0: // Time
step.durationType = Dimension.TIME;
step.durationValue = intervalTime;
break;
case 1: // Distance
step.durationType = Dimension.DISTANCE;
step.durationValue = intevalDistance;
break;
}
repeat.steps.add(step);
//noinspection ConstantIfStatement
if (true) {
Step rest = null;
switch (intervalRestType) {
case 0: // Time
rest = Step.createPauseStep(Dimension.TIME, intervalRestTime);
break;
case 1: // Distance
if (convertRestToRecovery == false) {
rest = Step.createPauseStep(Dimension.DISTANCE, intevalRestDistance);
} else {
rest = new Step();
rest.intensity = Intensity.RECOVERY;
rest.durationType = Dimension.DISTANCE;
rest.durationValue = intevalRestDistance;
}
break;
}
repeat.steps.add(rest);
}
}
w.steps.add(repeat);
if (cooldown) {
Step step = new Step();
step.intensity = Intensity.COOLDOWN;
step.durationType = null;
addAutoPauseTrigger(res, step, prefs);
w.steps.add(step);
}
return w;
}
public static boolean validateSeconds(String newValue) {
// TODO move this somewhere
long seconds = SafeParse.parseSeconds(newValue, -1);
long seconds2 = SafeParse.parseSeconds(DateUtils.formatElapsedTime(seconds), -1);
if (seconds == seconds2)
return true;
return false;
}
public static SharedPreferences getAudioCuePreferences(Context ctx, SharedPreferences pref,
String key) {
return getSubPreferences(ctx, pref, key,
ctx.getString(R.string.Default),
AudioCueSettingsActivity.SUFFIX);
}
public static SharedPreferences getSubPreferences(Context ctx, SharedPreferences pref,
String key, String defaultVal, String suffix) {
String name = pref.getString(key, null);
if (name == null || name.contentEquals(defaultVal)) {
return pref;
}
return ctx.getSharedPreferences(name + suffix, Context.MODE_PRIVATE);
}
public static void addAudioCuesToWorkout(Resources res, Workout w, SharedPreferences prefs) {
final boolean mute = prefs.getBoolean(res.getString(R.string.pref_mute_bool), false);
w.setMute(mute);
addAudioCuesToWorkout(res, w.steps, prefs);
}
private static void addAudioCuesToWorkout(Resources res, ArrayList<Step> steps,
SharedPreferences prefs) {
final boolean skip_startstop_cue = prefs.getBoolean(
res.getString(R.string.cueinfo_skip_startstop), false);
ArrayList<Trigger> triggers = createDefaultTriggers(res, prefs);
boolean silent = triggers.size() == 0;
final boolean coaching = prefs.getBoolean(res.getString(R.string.cueinfo_target_coaching),
true);
if (silent && coaching) {
for (Step s : steps) {
if (s.getTargetType() != null) {
silent = false;
break;
}
}
}
addPauseStopResumeTriggers(res, triggers, prefs);
if (!silent)
{
EventTrigger ev = new EventTrigger();
ev.event = Event.STARTED;
ev.scope = Scope.STEP;
ev.maxCounter = 1;
ev.triggerAction.add(new AudioFeedback(R.string.cue_lap_started));
triggers.add(ev);
EventTrigger ev2 = new EventTrigger(); // for autolap
ev2.event = Event.STARTED;
ev2.scope = Scope.LAP;
ev2.skipCounter = 1; // skip above
ev2.triggerAction.add(new AudioFeedback(R.string.cue_lap_started));
triggers.add(ev2);
if (prefs.getBoolean(res.getString(R.string.pref_cue_hrm_connection), false)) {
HRMStateTrigger hrmState = new HRMStateTrigger();
hrmState.triggerAction.add(new HRMStateChangeFeedback(hrmState));
triggers.add(hrmState);
}
}
Step stepArr[] = new Step[steps.size()];
steps.toArray(stepArr);
for (int i = 0; i < stepArr.length; i++) {
// Step prev = i == 0 ? null : stepArr[i-1];
Step step = stepArr[i];
Step next = i + 1 == stepArr.length ? null : stepArr[i + 1];
switch (step.getIntensity()) {
case REPEAT:
addAudioCuesToWorkout(res, ((RepeatStep) step).steps, prefs);
break;
case ACTIVE:
step.triggers.addAll(triggers);
if (!silent && (next == null || next.getIntensity() != step.getIntensity()))
{
EventTrigger ev = new EventTrigger();
ev.event = Event.COMPLETED;
ev.scope = Scope.STEP;
ev.triggerAction.add(new AudioFeedback(R.string.cue_lap_completed));
step.triggers.add(ev);
Trigger elt = hasEndOfLapTrigger(triggers);
if (elt != null) {
/** Add feedback after "end of lap" */
ev.triggerAction.addAll(elt.triggerAction);
/** suppress empty STEP COMPLETED */
ev.triggerSuppression.add(EndOfLapSuppression.EmptyLapSuppression);
/** And suppress last end of lap trigger */
elt.triggerSuppression.add(EndOfLapSuppression.EndOfLapSuppression);
}
}
checkDuplicateTriggers(step);
// {
// Log.e("WorkoutBuilder", "triggers: ");
// for (Trigger t : step.triggers) {
// System.err.print(t + " ");
// }
// Log.e("WorkoutBuilder", "");
// }
break;
case RECOVERY:
case RESTING: {
if (step.durationType != null) {
IntervalTrigger trigger = new IntervalTrigger();
trigger.dimension = step.durationType;
trigger.first = 1;
trigger.interval = 1;
trigger.scope = Scope.STEP;
trigger.triggerAction.add(new CountdownFeedback(Scope.STEP, step.durationType));
step.triggers.add(trigger);
}
addPauseStopResumeTriggers(res, step.triggers, prefs);
if (!silent) {
createAudioCountdown(step);
}
break;
}
case WARMUP:
case COOLDOWN:
addPauseStopResumeTriggers(res, step.triggers, prefs);
if (skip_startstop_cue == false) {
EventTrigger ev = new EventTrigger();
ev.event = Event.STARTED;
ev.scope = Scope.STEP;
ev.triggerAction.add(new AudioFeedback(step.getIntensity() == Intensity.WARMUP ?
R.string.cue_warmup_started : R.string.cue_cooldown_started));
step.triggers.add(ev);
}
break;
}
if (coaching && step.getTargetType() != null) {
Range range = step.getTargetValue();
int averageSeconds = SafeParse.parseInt(prefs.getString(
res.getString(R.string.pref_target_pace_moving_average_seconds), "20"), 20);
int graceSeconds = SafeParse.parseInt(
prefs.getString(res.getString(R.string.pref_target_pace_grace_seconds), "30"),
30);
TargetTrigger tr = new TargetTrigger(step.getTargetType(), averageSeconds,
graceSeconds);
tr.scope = Scope.STEP;
tr.range = range;
tr.triggerAction.add(new CoachFeedback(Scope.ACTIVITY, step.getTargetType(), range,
tr));
step.triggers.add(tr);
}
}
}
interface TriggerFilter {
boolean match(Trigger trigger);
}
private static Trigger hasTrigger(List<Trigger> triggers, TriggerFilter filter) {
for (Trigger t : triggers) {
if (filter.match(t))
return t;
}
return null;
}
private static Trigger hasEndOfLapTrigger(List<Trigger> triggers) {
return hasTrigger(triggers, new TriggerFilter() {
@Override
public boolean match(Trigger trigger) {
if (trigger == null)
return false;
if (!(trigger instanceof EventTrigger))
return false;
EventTrigger et = (EventTrigger) trigger;
return (et.event == Event.COMPLETED && et.scope == Scope.LAP);
}
});
}
private static void checkDuplicateTriggers(Step step) {
if (hasEndOfLapTrigger(step.triggers) != null) {
Log.e("WorkoutBuilder", "hasEndOfLapTrigger()");
/**
* The end of lap trigger can be a duplicate of a distance based
* interval trigger 1) in a step with distance duration, that is a
* multiple of the interval-distance e.g interval-trigger-distance =
* 100m duration = 1000m, then set max count = 9 2) in a step with
* autolap 500m and interval-trigger-distance 1000 then remove the
* trigger
*/
ArrayList<TriggerSuppression> list = new ArrayList<TriggerSuppression>();
if (step.getAutolap() > 0) {
list.add(new EndOfLapSuppression(step.getAutolap()));
}
if (step.getDurationType() == Dimension.DISTANCE) {
list.add(new EndOfLapSuppression(step.getDurationValue()));
}
for (Trigger t : step.triggers) {
if (!(t instanceof IntervalTrigger))
continue;
IntervalTrigger it = (IntervalTrigger) t;
if (it.dimension != Dimension.DISTANCE)
continue;
it.triggerSuppression.addAll(list);
}
}
}
private static ArrayList<Trigger> createDefaultTriggers(Resources res, SharedPreferences prefs) {
ArrayList<Feedback> feedback = new ArrayList<Feedback>();
ArrayList<Trigger> triggers = new ArrayList<Trigger>();
if (prefs.getBoolean(res.getString(R.string.cue_time), false)) {
long val = 0;
String vals = prefs.getString(res.getString(R.string.cue_time_intervall), "120");
try {
val = Long.parseLong(vals);
} catch (NumberFormatException e) {
}
if (val > 0) {
IntervalTrigger t = new IntervalTrigger();
t.first = val;
t.interval = val;
t.scope = Scope.STEP;
t.dimension = Dimension.TIME;
triggers.add(t);
}
}
if (prefs.getBoolean(res.getString(R.string.cue_distance), false)) {
long val = 0;
String vals = prefs.getString(res.getString(R.string.cue_distance_intervall), "1000");
try {
val = Long.parseLong(vals);
} catch (NumberFormatException e) {
}
if (val > 0) {
IntervalTrigger t = new IntervalTrigger();
t.first = val;
t.interval = val;
t.scope = Scope.STEP;
t.dimension = Dimension.DISTANCE;
triggers.add(t);
}
}
if (prefs.getBoolean(res.getString(R.string.cue_end_of_lap), false)) {
EventTrigger ev = new EventTrigger();
ev.event = Event.COMPLETED;
ev.scope = Scope.LAP;
triggers.add(ev);
}
addFeedbackFromPreferences(prefs, res, feedback);
for (Trigger t : triggers) {
t.triggerAction = feedback;
/** suppress empty laps */
t.triggerSuppression.add(EndOfLapSuppression.EmptyLapSuppression);
}
return triggers;
}
private static void addPauseStopResumeTriggers(Resources res, ArrayList<Trigger> list,
SharedPreferences prefs) {
if (prefs.getBoolean(res.getString(R.string.cueinfo_skip_startstop), false) == false) {
{
EventTrigger p = new EventTrigger();
p.event = Event.PAUSED;
p.scope = Scope.STEP;
p.triggerAction.add(new AudioFeedback(R.string.cue_activity_paused));
list.add(p);
}
{
EventTrigger r = new EventTrigger();
r.event = Event.RESUMED;
r.scope = Scope.STEP;
r.triggerAction.add(new AudioFeedback(R.string.cue_activity_resumed));
list.add(r);
}
{
EventTrigger ev = new EventTrigger();
ev.event = Event.STOPPED;
ev.scope = Scope.STEP;
ev.triggerAction.add(new AudioFeedback(R.string.cue_activity_stopped));
list.add(ev);
}
}
}
private static void createAudioCountdown(Step step) {
if (step.getDurationType() == null) {
return;
}
double first = 0;
ArrayList<Double> list = new ArrayList<Double>();
switch (step.getDurationType()) {
case TIME:
first = 60; // 1 minute
Double tmp0[] = {
60d, 30d, 10d, 5d, 3d, 2d, 1d
};
list.addAll(Arrays.asList(tmp0));
break;
case DISTANCE:
first = 100; // 100 meters
Double tmp1[] = {
100d, 50d, 20d, 10d
};
list.addAll(Arrays.asList(tmp1));
break;
default:
return;
}
if (step.getDurationValue() > first) {
/**
* If longer than limit...create a Interval trigger for ">" part
*/
IntervalTrigger trigger = new IntervalTrigger();
trigger.dimension = step.getDurationType();
trigger.scope = Scope.STEP;
trigger.first = first;
trigger.interval = first;
trigger.triggerAction
.add(new AudioCountdownFeedback(Scope.STEP, step.getDurationType()));
step.triggers.add(trigger);
}
/**
* Then create a list trigger for reminder...
*/
ArrayList<Double> triggerTimes = new ArrayList<Double>();
for (Double d : list) {
if (d >= step.getDurationValue())
continue;
double val = step.getDurationValue() - d;
if ((val % first) == 0) {
continue; // handled by interval trigger
}
double margin = 0.4d; // add a bit of margin, NOTE: less than 0.5
triggerTimes.add(d + margin);
}
{
ListTrigger trigger = new ListTrigger();
trigger.remaining = true;
trigger.dimension = step.getDurationType();
trigger.scope = Scope.STEP;
trigger.triggerTimes = triggerTimes;
trigger.triggerAction
.add(new AudioCountdownFeedback(Scope.STEP, step.getDurationType()));
step.triggers.add(trigger);
}
if (true) {
/**
* Add add information just when pause step starts...
*/
EventTrigger ev = new EventTrigger();
ev.event = Event.STARTED;
ev.scope = Scope.STEP;
ev.triggerAction.add(new AudioCountdownFeedback(Scope.STEP, step.getDurationType()));
step.triggers.add(ev);
}
}
public static void prepareWorkout(Resources res, SharedPreferences prefs, Workout w,
boolean basic) {
List<StepListEntry> steps = w.getStepList();
/**
* Add/remove autolap
*/
boolean autolap = prefs.getBoolean(res.getString(R.string.pref_autolap_active), false);
if (basic == false) {
autolap = prefs.getBoolean(res.getString(R.string.pref_step_autolap_active), autolap);
}
if (autolap) {
double val = 0;
String vals = prefs.getString(res.getString(R.string.pref_autolap), "1000");
try {
val = Double.parseDouble(vals);
} catch (NumberFormatException e) {
}
Log.i("WorkoutBuilder", "setAutolap(" + val + ")");
for (StepListEntry s : steps) {
s.step.setAutolap(0); // reset
switch (s.step.getIntensity()) {
case ACTIVE:
s.step.setAutolap(val);
break;
case RECOVERY:
case RESTING:
case WARMUP:
case COOLDOWN:
case REPEAT:
break;
}
}
}
/**
* Add countdowns after steps with duration "until pressed"
* - if next is not a countdown
* - and current is not rest
*/
if (prefs.getBoolean(res.getString(R.string.pref_step_countdown_active), true))
{
long val = 15; // default 15s
String vals = prefs.getString(res.getString(R.string.pref_step_countdown_time), "15");
try {
val = Long.parseLong(vals);
} catch (NumberFormatException e) {
}
if (val > 0) {
StepListEntry stepArr[] = new StepListEntry[steps.size()];
steps.toArray(stepArr);
for (int i = 0; i < stepArr.length; i++) {
// Step prev = i == 0 ? null : stepArr[i-1];
Step step = stepArr[i].step;
Step next = i + 1 == stepArr.length ? null : stepArr[i + 1].step;
if (step.durationType != null)
continue;
if (step.intensity == Intensity.REPEAT || step.intensity == Intensity.RESTING)
continue;
if (next == null)
continue;
if (next.durationType == Dimension.TIME && next.intensity == Intensity.RESTING)
continue;
Step s = Step.createPauseStep(Dimension.TIME, val);
if (stepArr[i].parent == null) {
w.steps.add(i + 1, s);
Log.e("WorkoutBuilder", "Added step at index: " + (i + 1));
} else {
RepeatStep rs = (RepeatStep) stepArr[i].parent;
int idx = rs.steps.indexOf(step);
rs.steps.add(idx, s);
Log.e("WorkoutBuilder", "Added step at index: " + (i + 1) + " repeat index: "
+ (idx + 1));
}
}
}
}
}
public static void addFeedbackFromPreferences(SharedPreferences prefs,
Resources res, ArrayList<Feedback> feedback) {
/**** TOTAL ****/
if (prefs.getBoolean(res.getString(R.string.cueinfo_total_distance), false)) {
feedback.add(new AudioFeedback(Scope.ACTIVITY, Dimension.DISTANCE));
}
if (prefs.getBoolean(res.getString(R.string.cueinfo_total_time), false)) {
feedback.add(new AudioFeedback(Scope.ACTIVITY, Dimension.TIME));
}
if (Dimension.SPEED_CUE_ENABLED
&& prefs.getBoolean(res.getString(R.string.cueinfo_total_speed), false)) {
feedback.add(new AudioFeedback(Scope.ACTIVITY, Dimension.SPEED));
}
if (prefs.getBoolean(res.getString(R.string.cueinfo_total_pace), false)) {
feedback.add(new AudioFeedback(Scope.ACTIVITY, Dimension.PACE));
}
if (prefs.getBoolean(res.getString(R.string.cueinfo_total_hr), false)) {
feedback.add(new AudioFeedback(Scope.ACTIVITY, Dimension.HR));
}
if (prefs.getBoolean(res.getString(R.string.cueinfo_total_hrz), false)) {
feedback.add(new AudioFeedback(Scope.ACTIVITY, Dimension.HRZ));
}
/**** STEP ****/
if (prefs.getBoolean(res.getString(R.string.cueinfo_step_distance), false)) {
feedback.add(new AudioFeedback(Scope.STEP, Dimension.DISTANCE));
}
if (prefs.getBoolean(res.getString(R.string.cueinfo_step_time), false)) {
feedback.add(new AudioFeedback(Scope.STEP, Dimension.TIME));
}
if (Dimension.SPEED_CUE_ENABLED
&& prefs.getBoolean(res.getString(R.string.cueinfo_step_speed), false)) {
feedback.add(new AudioFeedback(Scope.STEP, Dimension.SPEED));
}
if (prefs.getBoolean(res.getString(R.string.cueinfo_step_pace), false)) {
feedback.add(new AudioFeedback(Scope.STEP, Dimension.PACE));
}
if (prefs.getBoolean(res.getString(R.string.cueinfo_step_hr), false)) {
feedback.add(new AudioFeedback(Scope.STEP, Dimension.HR));
}
if (prefs.getBoolean(res.getString(R.string.cueinfo_step_hrz), false)) {
feedback.add(new AudioFeedback(Scope.STEP, Dimension.HRZ));
}
/**** LAP ****/
if (prefs.getBoolean(res.getString(R.string.cueinfo_lap_distance), false)) {
feedback.add(new AudioFeedback(Scope.LAP, Dimension.DISTANCE));
}
if (prefs.getBoolean(res.getString(R.string.cueinfo_lap_time), false)) {
feedback.add(new AudioFeedback(Scope.LAP, Dimension.TIME));
}
if (Dimension.SPEED_CUE_ENABLED
&& prefs.getBoolean(res.getString(R.string.cueinfo_lap_speed), false)) {
feedback.add(new AudioFeedback(Scope.LAP, Dimension.SPEED));
}
if (prefs.getBoolean(res.getString(R.string.cueinfo_lap_pace), false)) {
feedback.add(new AudioFeedback(Scope.LAP, Dimension.PACE));
}
if (prefs.getBoolean(res.getString(R.string.cueinfo_lap_hr), false)) {
feedback.add(new AudioFeedback(Scope.LAP, Dimension.HR));
}
if (prefs.getBoolean(res.getString(R.string.cueinfo_lap_hrz), false)) {
feedback.add(new AudioFeedback(Scope.LAP, Dimension.HRZ));
}
/**** CURRENT ****/
if (prefs.getBoolean(res.getString(R.string.cueinfo_current_pace), false)) {
feedback.add(new AudioFeedback(Scope.CURRENT, Dimension.PACE));
}
if (prefs.getBoolean(res.getString(R.string.cueinfo_current_speed), false)) {
feedback.add(new AudioFeedback(Scope.CURRENT, Dimension.SPEED));
}
if (prefs.getBoolean(res.getString(R.string.cueinfo_current_hr), false)) {
feedback.add(new AudioFeedback(Scope.CURRENT, Dimension.HR));
}
if (prefs.getBoolean(res.getString(R.string.cueinfo_current_hrz), false)) {
feedback.add(new AudioFeedback(Scope.CURRENT, Dimension.HRZ));
}
}
}