Beispiel #1
0
        /// <summary>
        /// Fill a collection of tasks by loading the content of a file
        /// </summary>
        public void LoadFromFile(string file)
        {
            //read the file line by line and gather these lines into groups
            String separator = GetTaskSeparator();

            _allTasks.Clear();
            StringBuilder        currentGroup = null;
            List <StringBuilder> listOfGroups = new List <StringBuilder>();

            using (StreamReader reader = new StreamReader(file))
            {
                while (!reader.EndOfStream)
                {
                    String line = reader.ReadLine();
                    if ((line == separator) || (currentGroup == null)) //begin of new group, add this group in the list
                    {
                        currentGroup = new StringBuilder();
                        listOfGroups.Add(currentGroup);
                    }
                    //add the line to the current group
                    currentGroup.AppendLine(line);
                }
            }
            //convert each group of lines into tasks and add them into the collection
            TaskToStringConvertor convertor = new TaskToStringConvertor();

            foreach (StringBuilder sb in listOfGroups)
            {
                TaskToDo task = convertor.StringToTask(sb.ToString());
                _allTasks.Add(task);
            }
        }
Beispiel #2
0
 /// <summary>
 /// Add a new subtask to the current task
 /// </summary>
 /// <param name="newSubtask"></param>
 /// <returns></returns>
 public TaskToDo AddSubtask(TaskToDo newSubtask)
 {
     newSubtask._parentTask = this; //create the uplink between this and the child
     _subtasks.Add(newSubtask);
     RefreshCompletedStatus(true);  //refresh the completed status of current task and all its parents
     return(newSubtask);
 }
Beispiel #3
0
        /// <summary>
        /// returns true if a given task can be moved down
        /// </summary>
        /// <param name="task"></param>
        /// <returns></returns>
        public Boolean CanMoveTaskDown(TaskToDo task)
        {
            int index     = _allTasks.IndexOf(task);
            int lastIndex = _allTasks.Count - 1;

            return((index >= 0) && (index < lastIndex));  //case where index is -1 is integrated in this condition
        }
Beispiel #4
0
 /// <summary>
 /// remove a given task from the collection
 /// </summary>
 /// <param name="taskToRemove"></param>
 public void RemoveTask(TaskToDo taskToRemove)
 {
     if (_allTasks.Contains(taskToRemove))
     {
         _allTasks.Remove(taskToRemove);
     }
 }
Beispiel #5
0
        /// <summary>
        /// replace a task in the collection by a new one
        /// </summary>
        /// <param name="taskToReplace"></param>
        /// <param name="taskToInsert"></param>
        public void ReplaceTask(TaskToDo taskToReplace, TaskToDo taskToInsert)
        {
            int index = _allTasks.IndexOf(taskToReplace);

            _allTasks.RemoveAt(index);
            _allTasks.Insert(index, taskToInsert);
        }
Beispiel #6
0
 /// <summary>
 /// Add a task into the collection
 /// returns the task that was added
 /// </summary>
 /// <param name="newTask"></param>
 /// <returns></returns>
 public TaskToDo AddTask(TaskToDo newTask)
 {
     if (!_allTasks.Contains(newTask))
     {
         _allTasks.Add(newTask);
     }
     return(newTask);
 }
Beispiel #7
0
 /// <summary>
 /// Remove a subtask
 /// </summary>
 /// <param name="subtaskToRemove"></param>
 public void RemoveSubtask(TaskToDo subtaskToRemove)
 {
     if (_subtasks.Contains(subtaskToRemove))
     {
         _subtasks.Remove(subtaskToRemove);
         RefreshCompletedStatus(true); //refresh the completed status of current task and all its parents
     }
 }
Beispiel #8
0
 /// <summary>
 /// constructor
 /// </summary>
 public TaskToDo(String name, String description)
 {
     _parentTask  = null;
     _name        = name;
     _subtasks    = new List <TaskToDo>();
     _description = description;
     _completed   = false;
 }
Beispiel #9
0
        /// <summary>
        /// convert a task to a string
        /// </summary>
        /// <param name="task"></param>
        /// <returns></returns>
        public String TaskToString(TaskToDo task)
        {
            if (task == null)
            {
                return(String.Empty);
            }
            StringBuilder sb = new StringBuilder();

            RecursiveTaskToString(task, 0, sb);
            return(sb.ToString());
        }
Beispiel #10
0
        /// <summary>
        /// Move a given task up -swap it with previous task)
        /// </summary>
        /// <param name="task"></param>
        public void MoveTaskUp(TaskToDo task)
        {
            int currentIndex = _allTasks.IndexOf(task);

            if (currentIndex < 1)
            {
                return;
            }
            _allTasks.RemoveAt(currentIndex);
            _allTasks.Insert(currentIndex - 1, task);
        }
Beispiel #11
0
        /// <summary>
        /// Move a given task down (swap it with next task)
        /// </summary>
        /// <param name="task"></param>
        public void MoveTaskDown(TaskToDo task)
        {
            int currentIndex = _allTasks.IndexOf(task);
            int lastIndex    = _allTasks.Count - 1;

            if (currentIndex < 0 || currentIndex >= lastIndex)
            {
                return;
            }
            _allTasks.RemoveAt(currentIndex);
            _allTasks.Insert(currentIndex + 1, task);
        }
Beispiel #12
0
        /// <summary>
        /// returns the taskTodo that is just after the current task at the same level
        /// returns null if there is no next brother
        /// </summary>
        /// <returns></returns>
        public TaskToDo NextBrother()
        {
            TaskToDo result = null;

            if (_parentTask != null)
            {
                int currentIndex = _parentTask._subtasks.IndexOf(this);
                if (currentIndex < (_parentTask._subtasks.Count - 1))
                {
                    result = _parentTask._subtasks[currentIndex + 1];
                }
            }
            return(result);
        }
Beispiel #13
0
        /// <summary>
        /// returns the taskTodo that is just before the current task at the same level
        /// returns null if there is no previous brother
        /// </summary>
        /// <returns></returns>
        public TaskToDo PreviousBrother()
        {
            TaskToDo result = null;

            if (_parentTask != null)
            {
                int currentIndex = _parentTask._subtasks.IndexOf(this);
                if (currentIndex > 0)
                {
                    result = _parentTask._subtasks[currentIndex - 1];
                }
            }
            return(result);
        }
 /// <summary>
 /// Count recursively the number of terminal tasks and the number of terminal tasks that are completed
 /// </summary>
 /// <param name="task"></param>
 private void RecursiveUpdate(TaskToDo task)
 {
     if (task.IsTerminalTask)
     {
         _totalNbTerminalTasks++;
         if (task.IsCompleted)
         {
             _totalNbCompletedTasks++;
         }
     }
     else
     {
         foreach (TaskToDo subtask in task.Subtasks)
         {
             RecursiveUpdate(subtask);
         }
     }
 }
Beispiel #15
0
        /// <summary>
        /// write
        /// </summary>
        /// <param name="task"></param>
        /// <param name="indentationLevel"></param>
        /// <param name="strToWrite"></param>
        private void RecursiveTaskToString(TaskToDo task, int indentationLevel, StringBuilder strToWrite)
        {
            //write name
            strToWrite.AppendLine(String.Format("{0}- {1}{2}", new String('\t', indentationLevel), task.Name, task.IsCompleted ? " [OK]" : String.Empty));
            //write description (possibly on several lines)
            if (!String.IsNullOrEmpty(task.Description))
            {
                String[] lines = task.Description.SplitLines(false);
                foreach (String line in lines)
                {
                    strToWrite.AppendLine(new string('\t', indentationLevel + 1) + line);
                }
                //add a blank line beetween description and subtasks
                strToWrite.AppendLine();
            }

            //write subtasks
            foreach (TaskToDo subtask in task.Subtasks)
            {
                RecursiveTaskToString(subtask, indentationLevel + 1, strToWrite);
            }
        }
 /// <summary>
 /// update the current progression from a given task
 /// </summary>
 /// <param name="task"></param>
 public void UpdateFromTask(TaskToDo task)
 {
     _totalNbCompletedTasks = 0;
     _totalNbTerminalTasks  = 0;
     RecursiveUpdate(task);
 }
 /// <summary>
 /// Constructor from a given task
 /// </summary>
 public TaskProgression(TaskToDo task)
 {
     UpdateFromTask(task);
 }
Beispiel #18
0
        /// <summary>
        /// parse a string and convert it into a task
        /// </summary>
        /// <param name="strToParse"></param>
        /// <returns></returns>
        public TaskToDo StringToTask(String strToParse)
        {
            TaskToDo rootTask                    = null;
            TaskToDo lastTask                    = null;
            int      lastIndentation             = 0;
            Stack <Tuple <int, TaskToDo> > stack = new Stack <Tuple <int, TaskToDo> >();


            String[] lines = strToParse.SplitLines(true);
            foreach (String line in lines)
            {
                int      indentation = 0;
                String   content;
                LineType type = ParseLine(line, out indentation, out content);
                switch (type)
                {
                case LineType.Empty:     //ignore empty line
                    break;

                case LineType.Comment:     //comment, ignore it
                    break;

                case LineType.Description:    //Description of the current task (could be on several lines)
                    if (lastTask != null)     //if there is no current task, the description is ignored
                    {
                        if (!String.IsNullOrEmpty(lastTask.Description))
                        {
                            lastTask.Description += Environment.NewLine;
                        }
                        lastTask.Description += content;
                    }
                    break;

                case LineType.Task:       //task or subtask
                    TaskToDo newTask = ParseTaskLine(content);
                    if (lastTask == null) //this is the first task, use it as root
                    {
                        rootTask = newTask;
                        lastTask = newTask;
                    }
                    else                                   //not the first task, insert it in the existing tree
                    {
                        if (indentation > lastIndentation) //newTask is a subtask of last task
                        {
                            lastTask.AddSubtask(newTask);
                        }
                        else     //we have to go back in tree to find a parent
                        {
                            Boolean parentFound = false;
                            while (!parentFound)
                            {
                                if (stack.Count == 0)
                                {
                                    throw new ApplicationException("Indentation smaller than root level");
                                }
                                var upperLevel = stack.Peek();
                                if (upperLevel.Item1 < indentation)    //parent found
                                {
                                    parentFound = true;
                                    upperLevel.Item2.AddSubtask(newTask);
                                }
                                else             //not found yet
                                {
                                    stack.Pop(); //go to level up
                                }
                            }                    //end of search for parents
                        }                        //end of "Not subtask of last task
                    }                            //end of "Not root"
                    //save state for next loop
                    stack.Push(new Tuple <int, TaskToDo>(indentation, newTask));
                    lastTask        = newTask;
                    lastIndentation = indentation;
                    break;

                default:     //ignore all other lines
                    break;
                }
            } //end foreach line
            return(rootTask);
        }
Beispiel #19
0
        /// <summary>
        /// parse a task line and returns the corresponding task including its attributes
        /// </summary>
        /// <param name="contentToParse"></param>
        /// <returns></returns>
        private TaskToDo ParseTaskLine(String contentToParse)
        {
            //remove (and check) the '-' that starts the line
            if (!contentToParse.StartsWith("-"))
            {
                throw new ApplicationException("Task line must begin with a -");
            }
            //browse the string to separate the name and all attributes (between [])
            StringBuilder sbName             = new StringBuilder();
            List <String> attributes         = new List <string>();
            StringBuilder sbCurrentAttribute = new StringBuilder();
            Boolean       inAttribute        = false;

            for (int i = 1; i < contentToParse.Length; i++) //starts from 1 to ignore the '-'
            {
                char c = contentToParse[i];
                switch (c)
                {
                case '[':     //starts a new attribute
                    if (inAttribute)
                    {
                        throw new ApplicationException("Recursive attribute ([[)");                  //already in an attribute, not managed
                    }
                    inAttribute = true;
                    sbCurrentAttribute.Clear();
                    break;

                case ']':     //ends an attribute
                    if (!inAttribute)
                    {
                        throw new ApplicationException("End of attribute without begin (])");
                    }
                    attributes.Add(sbCurrentAttribute.ToString());
                    sbCurrentAttribute.Clear();
                    inAttribute = false;
                    break;

                default:     //any other character
                    if (inAttribute)
                    {
                        sbCurrentAttribute.Append(c);
                    }
                    else
                    {
                        sbName.Append(c);
                    }
                    break;
                }
            }
            //check we have not begun an attribute and is not finished
            if (inAttribute)
            {
                throw new ApplicationException("Attribute started but without end ([)");
            }
            //create the task with trimmed name
            TaskToDo result = new TaskToDo(sbName.ToString().Trim(), String.Empty);

            //check each attribute
            foreach (String attribute in attributes)
            {
                if (attribute == "OK")
                {
                    result.SetCompleted();
                }
                else
                {
                    throw new ApplicationException("Unknwon attribute : " + attribute);
                }
            }
            return(result);
        }
Beispiel #20
0
        /// <summary>
        /// returns true if a given task can be moved up
        /// </summary>
        /// <param name="task"></param>
        /// <returns></returns>
        public Boolean CanMoveTaskUp(TaskToDo task)
        {
            int index = _allTasks.IndexOf(task);

            return(index > 0); //case where index is -1 is integrated in this condition
        }
Beispiel #21
0
        /// <summary>
        /// Create a task without subtasks
        /// </summary>
        /// <param name="name"></param>
        /// <param name="description"></param>
        /// <returns></returns>
        public static TaskToDo CreateTaskWithoutChild(String name, string description)
        {
            TaskToDo result = new TaskToDo(name, description);

            return(result);
        }