5353import java .time .LocalDate ;
5454import java .time .ZoneId ;
5555import java .util .ArrayList ;
56+ import java .util .Comparator ;
5657import java .util .Locale ;
5758import java .util .stream .Collectors ;
5859import java .util .stream .Stream ;
@@ -285,7 +286,7 @@ public JSONObject call() {
285286 try {
286287 if (data != null && data .has ("data" ) && data .getInt ("statusCode" ) == 200 ) {
287288 ArrayList <Task > subtaskData = JSONToModel .convertJSONToTasks (data .getJSONArray ("data" ));
288- setSubtasks (subtaskData );
289+ setSubtasksTableContent (subtaskData );
289290 getTaskData ().setSubtasks (subtaskData );
290291 }
291292 } catch (JSONException e ) {
@@ -639,10 +640,44 @@ public void onComplete(JSONObject result) {
639640 Task subtask = new Task (newSubtaskField .getText ().toString ());
640641 subtask .setId (result .getJSONObject ("data" ).getInt ("id" ));
641642
642- getTaskData ().getSubtasks ().add (subtask );
643-
644- // Add right before "new subtask" row (1-indexed)
645- subtaskList .addView (addSubtaskToTable (subtask ), subtaskList .getChildCount () - 1 );
643+ /*
644+ * Add right after last incomplete task using binary search for the last incomplete subtask
645+ * The algorithm is as follows:
646+ * 1. Start at first element and check if complete
647+ * 2. If complete, then
648+ * 3. If the first element OR the previous element is incomplete, then
649+ * ADD SUBTASK; END
650+ * 4. Else, (previous element is complete), then
651+ * (the last incomplete subtask is BEFORE i) divide i by 2 and REPEAT
652+ * 7. Else, (current element is incomplete), then
653+ * (the last incomplete subtask is AFTER i) set i to be between its current value
654+ * and the index of the last element
655+ */
656+ ArrayList <Task > currSubtasks = getTaskData ().getSubtasks ();
657+ int i = getTaskData ().getSubtasks ().size () / 2 ;
658+ Log .d ("Size" , String .valueOf (i * 2 ));
659+ while (i < getTaskData ().getSubtasks ().size ()) {
660+ Log .d ("i" , String .valueOf (i ));
661+ if (currSubtasks .get (i ).isCompleted ()) {
662+ if (i == 0 || !currSubtasks .get (i - 1 ).isCompleted ()) {
663+ getTaskData ().addSubtask (i , subtask );
664+ subtaskList .addView (addSubtaskToTable (subtask ), i );
665+ Log .d ("status" , "breaking now" );
666+ break ;
667+ } else {
668+ i /= 2 ;
669+ }
670+ } else {
671+ if (i != currSubtasks .size () - 1 && currSubtasks .get (i + 1 ).isCompleted ()) {
672+ getTaskData ().addSubtask (i , subtask );
673+ subtaskList .addView (addSubtaskToTable (subtask ), i + 1 );
674+ Log .d ("status" , "breaking now" );
675+ break ;
676+ } else {
677+ i = (currSubtasks .size () + i ) / 2 ;
678+ }
679+ }
680+ }
646681
647682 ((EditText ) subtaskList .findViewById (R .id .newSubtaskFieldId )).setText ("" );
648683 }
@@ -661,7 +696,9 @@ public void onDeleteSubtaskClick(View view) {
661696 new DeleteJottingRequest ((Integer ) subtaskRow .getTag (), getUserApiKey (), "task" ), data -> {
662697 if (data != null ) {
663698 if (data .optInt ("statusCode" ) == 200 ) {
664- ((ViewGroup ) subtaskRow .getParent ()).removeView (subtaskRow );
699+ TableLayout subtaskTable = (TableLayout ) subtaskRow .getParent ();
700+ getTaskData ().getSubtasks ().remove (subtaskTable .indexOfChild (subtaskRow ));
701+ subtaskTable .removeView (subtaskRow );
665702 }
666703 }
667704 }
0 commit comments