diff --git a/app/src/main/java/com/ridgebotics/ridgescout/MainActivity.java b/app/src/main/java/com/ridgebotics/ridgescout/MainActivity.java index 9ce3fd9..f98b427 100644 --- a/app/src/main/java/com/ridgebotics/ridgescout/MainActivity.java +++ b/app/src/main/java/com/ridgebotics/ridgescout/MainActivity.java @@ -73,7 +73,7 @@ public class MainActivity extends AppCompatActivity { appBarConfiguration = new AppBarConfiguration.Builder( R.id.navigation_scouting, - R.id.navigation_data, + R.id.navigation_data_parent, R.id.navigation_transfer, R.id.navigation_settings) .build(); diff --git a/app/src/main/java/com/ridgebotics/ridgescout/types/frcEvent.java b/app/src/main/java/com/ridgebotics/ridgescout/types/frcEvent.java index c1b7515..066e029 100644 --- a/app/src/main/java/com/ridgebotics/ridgescout/types/frcEvent.java +++ b/app/src/main/java/com/ridgebotics/ridgescout/types/frcEvent.java @@ -120,6 +120,18 @@ public class frcEvent { return maxMatch; } + public frcMatch getNextTeamMatch(int teamNum, int curMatch){ + frcMatch[] teamMatches = getTeamMatches(teamNum); + + for(int i = 0; i < teamMatches.length; i++) { + if (teamMatches[i].matchIndex > curMatch) + return teamMatches[i]; + + } + + return null; + } + // public // Returns the soonest match that there will be all the possible upcoming data on other teams @@ -144,4 +156,13 @@ public class frcEvent { } } } + + public frcTeam getTeamByNum(int teamNum){ + for(int i = 0; i < teams.size(); i++){ + frcTeam team = teams.get(i); + if(team.teamNumber == teamNum) + return team; + } + return null; + } } diff --git a/app/src/main/java/com/ridgebotics/ridgescout/ui/CandlestickView.java b/app/src/main/java/com/ridgebotics/ridgescout/ui/CandlestickView.java index 4e802cd..167f697 100644 --- a/app/src/main/java/com/ridgebotics/ridgescout/ui/CandlestickView.java +++ b/app/src/main/java/com/ridgebotics/ridgescout/ui/CandlestickView.java @@ -200,8 +200,13 @@ public class CandlestickView extends View { teamDataArray[i] = (int) teamData.get(i).get(); } - float lowerQuartile = DataProcessing.calculatePercentile(teamDataArray, 25); - float upperQuartile = DataProcessing.calculatePercentile(teamDataArray, 75); + float lowerQuartile = 0; + float upperQuartile = 0; + + if(teamDataArray.length != 0) { + lowerQuartile = DataProcessing.calculatePercentile(teamDataArray, 25); + upperQuartile = DataProcessing.calculatePercentile(teamDataArray, 75); + } System.out.println(locmin + ", " + lowerQuartile + ", " + avg + ", " + upperQuartile + ", " + locmax); setData(locmin, lowerQuartile, avg, upperQuartile, locmax, absmin, absmax); diff --git a/app/src/main/java/com/ridgebotics/ridgescout/ui/data/DataFragment.java b/app/src/main/java/com/ridgebotics/ridgescout/ui/data/DataFragment.java index 89c3fb0..2fd574f 100644 --- a/app/src/main/java/com/ridgebotics/ridgescout/ui/data/DataFragment.java +++ b/app/src/main/java/com/ridgebotics/ridgescout/ui/data/DataFragment.java @@ -20,6 +20,7 @@ import android.view.ViewGroup; import androidx.annotation.NonNull; import androidx.annotation.Nullable; import androidx.fragment.app.Fragment; +import androidx.fragment.app.FragmentTransaction; import com.ridgebotics.ridgescout.R; import com.ridgebotics.ridgescout.types.frcTeam; @@ -84,9 +85,6 @@ public class DataFragment extends Fragment { } public void load_teams(){ - DataManager.reload_event(); - - if(event == null) return; int[] teamNums = new int[event.teams.size()]; @@ -113,7 +111,8 @@ public class DataFragment extends Fragment { frcTeam finalTeam = team; teamRow.setOnClickListener(v -> { TeamsFragment.setTeam(finalTeam); - findNavController(this).navigate(R.id.action_navigation_data_to_navigation_data_teams); + ((DataParentFragment) getParentFragment()).moveToFragment(new TeamsFragment()); +// findNavController(this).navigate(R.id.action_navigation_data_parent_to_navigation_data_teams); }); } } @@ -131,7 +130,8 @@ public class DataFragment extends Fragment { final int fi = i; tr.setOnClickListener(v -> { FieldDataFragment.setFieldIndex(fi); - findNavController(this).navigate(R.id.action_navigation_data_to_navigation_data_field_data); + ((DataParentFragment) getParentFragment()).moveToFragment(new FieldDataFragment()); +// findNavController(get).navigate(R.id.action_navigation_data_parent_to_navigation_data_field_data); }); } } diff --git a/app/src/main/java/com/ridgebotics/ridgescout/ui/data/DataParentFragment.java b/app/src/main/java/com/ridgebotics/ridgescout/ui/data/DataParentFragment.java new file mode 100644 index 0000000..2883678 --- /dev/null +++ b/app/src/main/java/com/ridgebotics/ridgescout/ui/data/DataParentFragment.java @@ -0,0 +1,129 @@ +package com.ridgebotics.ridgescout.ui.data; + + +import static android.view.View.GONE; +import static android.view.View.VISIBLE; +import static androidx.navigation.fragment.FragmentKt.findNavController; +import static com.ridgebotics.ridgescout.utility.Colors.datafragment_option_1; +import static com.ridgebotics.ridgescout.utility.Colors.datafragment_option_2; +import static com.ridgebotics.ridgescout.utility.DataManager.evcode; +import static com.ridgebotics.ridgescout.utility.DataManager.event; +import static com.ridgebotics.ridgescout.utility.DataManager.match_latest_values; + +import android.os.Bundle; +import android.view.LayoutInflater; +import android.view.View; +import android.view.ViewGroup; + +import androidx.annotation.NonNull; +import androidx.annotation.Nullable; +import androidx.fragment.app.Fragment; +import androidx.fragment.app.FragmentTransaction; + +import com.ridgebotics.ridgescout.R; +import com.ridgebotics.ridgescout.databinding.FragmentDataParentBinding; +import com.ridgebotics.ridgescout.types.frcMatch; +import com.ridgebotics.ridgescout.types.frcTeam; +import com.ridgebotics.ridgescout.ui.FieldBorderedRow; +import com.ridgebotics.ridgescout.ui.TeamListOption; +import com.ridgebotics.ridgescout.utility.DataManager; +import com.ridgebotics.ridgescout.utility.SettingsManager; + +import java.util.ArrayList; +import java.util.Arrays; +import java.util.List; + +public class DataParentFragment extends Fragment { + + private FragmentDataParentBinding binding; + + private DataFragment dataFragment; + + private boolean editBoxEnabled = true; + + + public View onCreateView(@NonNull LayoutInflater inflater, @Nullable ViewGroup container, + @Nullable Bundle savedInstanceState) { + + binding = FragmentDataParentBinding.inflate(inflater, container, false); + DataManager.reload_event(); + + if (savedInstanceState == null && dataFragment == null){ + dataFragment = new DataFragment(); + + //add child fragment + getChildFragmentManager() + .beginTransaction() + .add(R.id.data_subfragment, dataFragment, "Data Subfragment") + .commit(); + } + + if(evcode.equals("unset") || event == null){ + binding.reportToggleButton.setVisibility(GONE); + return binding.getRoot(); + } + + binding.reportToggleButton.setOnClickListener(view -> { + editBoxEnabled =! editBoxEnabled; + binding.ScoutingEditBox.setVisibility(editBoxEnabled ? GONE : VISIBLE); + binding.reportToggleButton.setText(editBoxEnabled ? "▲ report" : "▼ report"); + }); + + generateScoutingTemplate(SettingsManager.getMatchNum()); + + return binding.getRoot(); + } + + public void moveToFragment(Fragment newFragment){ + // consider using Java coding conventions (upper first char class names!!!) + FragmentTransaction transaction = getChildFragmentManager().beginTransaction(); + // Replace whatever is in the fragment_container view with this fragment, + // and add the transaction to the back stack + transaction.replace(R.id.data_subfragment, newFragment); + transaction.addToBackStack(null); + // Commit the transaction + transaction.commit(); + } + + + // Generate format for scouting data + public void generateScoutingTemplate(int currentMatch){ + + int teamNum = SettingsManager.getTeamNum(); + boolean isBlueAlliance = false; + + + frcMatch nextMatch = event.getNextTeamMatch(teamNum, currentMatch); + + + List ourAlliance = new ArrayList<>(); + List opposingAlliance = new ArrayList<>(); + + for(int a = 0; a < nextMatch.blueAlliance.length; a++) + if(nextMatch.blueAlliance[a] != teamNum){ + (!isBlueAlliance ? ourAlliance : opposingAlliance).add(event.getTeamByNum(nextMatch.blueAlliance[a])); + } + for(int a = 0; a < nextMatch.redAlliance.length; a++) + if(nextMatch.redAlliance[a] != teamNum){ + (isBlueAlliance ? ourAlliance : opposingAlliance).add(event.getTeamByNum(nextMatch.redAlliance[a])); + } + + + String output = "Match: " + (nextMatch.matchIndex+1) + "\n"; + + output += "## Our Alliance ##"; + output += getTeamNameAndNum(ourAlliance.get(0)); + output += getTeamNameAndNum(ourAlliance.get(1)); + output += "\n## Opposing Alliance ##"; + output += getTeamNameAndNum(opposingAlliance.get(0)); + output += getTeamNameAndNum(opposingAlliance.get(1)); + output += getTeamNameAndNum(opposingAlliance.get(2)); + + binding.scoutingReportEdittext.setText(output); + + } + + private static String getTeamNameAndNum(frcTeam team){ + return "\n" + team.teamNumber + " " + team.teamName + ": \n"; + } +} \ No newline at end of file diff --git a/app/src/main/java/com/ridgebotics/ridgescout/ui/scouting/MatchScoutingFragment.java b/app/src/main/java/com/ridgebotics/ridgescout/ui/scouting/MatchScoutingFragment.java index 1fa7ada..ea36b8a 100644 --- a/app/src/main/java/com/ridgebotics/ridgescout/ui/scouting/MatchScoutingFragment.java +++ b/app/src/main/java/com/ridgebotics/ridgescout/ui/scouting/MatchScoutingFragment.java @@ -109,6 +109,11 @@ public class MatchScoutingFragment extends Fragment { create_fields(); update_scouting_data(); + if(DataManager.scoutNotice.isEmpty()) + binding.scoutingNoticeBox.setVisibility(View.GONE); + else + binding.scoutingNoticeText.setText(DataManager.scoutNotice); + return binding.getRoot(); } diff --git a/app/src/main/java/com/ridgebotics/ridgescout/ui/scouting/PitScoutingFragment.java b/app/src/main/java/com/ridgebotics/ridgescout/ui/scouting/PitScoutingFragment.java index c4570fb..7e65d79 100644 --- a/app/src/main/java/com/ridgebotics/ridgescout/ui/scouting/PitScoutingFragment.java +++ b/app/src/main/java/com/ridgebotics/ridgescout/ui/scouting/PitScoutingFragment.java @@ -56,6 +56,10 @@ public class PitScoutingFragment extends Fragment { return binding.getRoot(); } + if(DataManager.scoutNotice.isEmpty()) + binding.scoutingNoticeBox.setVisibility(View.GONE); + else + binding.scoutingNoticeText.setText(DataManager.scoutNotice); loadTeam(); diff --git a/app/src/main/java/com/ridgebotics/ridgescout/ui/scouting/ScoutingFragment.java b/app/src/main/java/com/ridgebotics/ridgescout/ui/scouting/ScoutingFragment.java index ae5579e..9174ee7 100644 --- a/app/src/main/java/com/ridgebotics/ridgescout/ui/scouting/ScoutingFragment.java +++ b/app/src/main/java/com/ridgebotics/ridgescout/ui/scouting/ScoutingFragment.java @@ -124,16 +124,11 @@ public class ScoutingFragment extends Fragment { binding.textName.setText("Welcome, " + SettingsManager.getUsername() + "!"); - int nextMatch = -1; - int teamNum = SettingsManager.getTeamNum(); - for(int i = SettingsManager.getMatchNum(); i < event.matches.size(); i++){ // Loop through matches and find next match - boolean foundMatch = false; - for(int a = 0; a < 3; a++) if(event.matches.get(i).blueAlliance[a] == teamNum){nextMatch = i+1; foundMatch = true;} - for(int a = 0; a < 3; a++) if(event.matches.get(i).redAlliance[a] == teamNum){nextMatch = i+1; foundMatch = true;} - if(foundMatch) break; - } + int matchNum = SettingsManager.getMatchNum(); + int nextMatch = event.getNextTeamMatch(SettingsManager.getTeamNum(), matchNum).matchIndex; + binding.textNextMatch.setText("Our next match: Match " + nextMatch); - binding.textMatchAlliance.setText("Match: " + (SettingsManager.getMatchNum()+1) + ", " + SettingsManager.getAllyPos()); + binding.textMatchAlliance.setText("Match: " + (matchNum+1) + ", " + SettingsManager.getAllyPos()); binding.textRescoutIndicator.setText("Things to rescout: " + DataManager.rescout_list.size()); return binding.getRoot(); diff --git a/app/src/main/java/com/ridgebotics/ridgescout/ui/settings/SettingsFragment.java b/app/src/main/java/com/ridgebotics/ridgescout/ui/settings/SettingsFragment.java index ce76cd2..39317b0 100644 --- a/app/src/main/java/com/ridgebotics/ridgescout/ui/settings/SettingsFragment.java +++ b/app/src/main/java/com/ridgebotics/ridgescout/ui/settings/SettingsFragment.java @@ -16,7 +16,9 @@ import static com.ridgebotics.ridgescout.utility.SettingsManager.defaults; import static com.ridgebotics.ridgescout.utility.SettingsManager.getEditor; import static com.ridgebotics.ridgescout.utility.SettingsManager.prefs; +import android.app.AlertDialog; import android.content.Context; +import android.content.DialogInterface; import android.os.Bundle; import android.text.Editable; import android.text.InputType; @@ -25,7 +27,10 @@ import android.view.Gravity; import android.view.LayoutInflater; import android.view.View; import android.view.ViewGroup; +import android.widget.Button; +import android.widget.EditText; import android.widget.LinearLayout; +import android.widget.ScrollView; import android.widget.TextView; import androidx.annotation.NonNull; @@ -130,6 +135,14 @@ public class SettingsFragment extends Fragment { binding.SettingsTable.removeAllViews(); manager.getView(binding.SettingsTable); + + if(!DataManager.getevcode().equals("unset")){ + Button editNoticeButton = new Button(getContext()); + editNoticeButton.setText("Edit Scout Notice"); + binding.SettingsTable.addView(editNoticeButton); + editNoticeButton.setOnClickListener(v->editNotice()); + } + } @@ -141,6 +154,27 @@ public class SettingsFragment extends Fragment { } + private void editNotice(){ + ScrollView sv = new ScrollView(getContext()); + EditText editText = new EditText(getContext()); + editText.setText(DataManager.scoutNotice); + sv.addView(editText); + + + AlertDialog.Builder alert = new AlertDialog.Builder(getContext()); + alert.setTitle("Edit Notice"); + alert.setView(sv); + alert.setNeutralButton("Cancel", null); + alert.setPositiveButton("Save", (dialogInterface, i) -> { + DataManager.scoutNotice = editText.getText().toString(); + DataManager.save_scout_notice(); + }); + alert.setCancelable(false); + + alert.create().show(); + } + + diff --git a/app/src/main/java/com/ridgebotics/ridgescout/utility/DataManager.java b/app/src/main/java/com/ridgebotics/ridgescout/utility/DataManager.java index 0a33f7e..cd1aa52 100644 --- a/app/src/main/java/com/ridgebotics/ridgescout/utility/DataManager.java +++ b/app/src/main/java/com/ridgebotics/ridgescout/utility/DataManager.java @@ -25,8 +25,9 @@ public class DataManager { SettingsManager.setEVCode("unset"); evcode = "unset"; }else{ - AlertManager.toast("Reloaded event!"); reload_rescout_list(); + reload_scout_notice(); + AlertManager.toast("Reloaded event!"); } } @@ -90,4 +91,36 @@ public class DataManager { AlertManager.error("Error saving scout fields", e); } } + + public static String scoutNotice = ""; + + public static void reload_scout_notice(){ + if(!FileEditor.fileExist(evcode + ".scoutnotice")) {scoutNotice = ""; return;} + byte[] file = FileEditor.readFile(evcode + ".scoutnotice"); + if(file == null) {scoutNotice = ""; return;} + + try { + BuiltByteParser bbp = new BuiltByteParser(file); + scoutNotice = (String) (bbp.parse().get(0).get()); + + } catch (Exception e){ + AlertManager.error("Error loading scout notice", e); + rescout_list = new ArrayList<>(); + } + } + + public static void save_scout_notice() { + try { + if(scoutNotice.isEmpty()){ + FileEditor.deleteFile(evcode + ".scoutnotice"); + return; + } + + ByteBuilder bb = new ByteBuilder(); + bb.addString(scoutNotice); + FileEditor.writeFile(evcode + ".scoutnotice", bb.build()); + } catch (Exception e){ + AlertManager.error("Error saving scout notice", e); + } + } } diff --git a/app/src/main/res/layout/fragment_data.xml b/app/src/main/res/layout/fragment_data.xml index d9c43ee..093e1e4 100644 --- a/app/src/main/res/layout/fragment_data.xml +++ b/app/src/main/res/layout/fragment_data.xml @@ -28,6 +28,7 @@ + + + + + + + + + + + + + + +