package de.renew.navigator.models;

import java.util.ArrayList;
import java.util.LinkedList;
import java.util.List;


/**
 * @author Konstantin Simon Maria Moellers
 * @version 2015-08-25
 */
public final class NavigatorFileTree extends Model {

    private List<SearchFilter> _activeFileFilters;
    private SearchFilter _textSearch;
    private final List<BackgroundTask> _backgroundTasks;

    /**
     * Constructor.
     */
    public NavigatorFileTree() {
        super();
        _activeFileFilters = new ArrayList<>();
        _backgroundTasks = new LinkedList<>();
    }

    /**
     * This is a getter which gets the list of search filters for the navigator file tree.
     * @return _activeFileFilters the list of search filters.
     */
    public List<SearchFilter> getActiveFileFilters() {
        return _activeFileFilters;
    }

    /**
     * This is a setter which sets the list of search filters for the navigator file tree.
     * @param activeFileFilters The list of search filters that should be set.
     */
    public void setActiveFileFilters(List<SearchFilter> activeFileFilters) {
        this._activeFileFilters = activeFileFilters;
        setChanged();
    }

    /**
     * This is a getter which gets the list of tree elements for the navigator file tree.
     * @return elements the list of tree elements.
     */
    public List<TreeElement> getTreeRoots() {
        return _elements;
    }

    /**
     * Activates a file filter on this navigator model.
     *
     * @param fileFilter the filter which should be activated
     */
    public void activateFileFilter(SearchFilter fileFilter) {
        this._activeFileFilters.add(fileFilter);

        // Inform observers.
        setChanged();
    }

    /**
     * Deactivates a file filter on this navigator model.
     *
     * @param fileFilter the filter which should be activated
     */
    public void deactivateFileFilter(SearchFilter fileFilter) {
        if (!this._activeFileFilters.remove(fileFilter)) {
            throw new IllegalArgumentException(
                String.format("The file filter was not activated yet: %s", fileFilter));
        }

        // Inform observers.
        setChanged();
    }

    /**
     * Deactivates a file filter by its name.
     *
     * @param name of the filter
     */
    public void deactivateFileFilter(String name) {
        SearchFilter filter = getFileFilterByName(name);

        if (filter == null) {
            return;
        }

        deactivateFileFilter(filter);
    }

    /**
     * Finds a file filter by its name.
     *
     * @param name of the file filter
     * @return null, if none found
     */
    public SearchFilter getFileFilterByName(String name) {
        for (SearchFilter filter : _activeFileFilters) {
            if (filter.getName().equals(name)) {
                return filter;
            }
        }

        return null;
    }

    /**
     * Clears all tree roots.
     */
    public void clearTreeRoots() {
        _elements.clear();
        setChanged();
    }

    /**
     * Expands all root directories.
     */
    public void expandAll() {
        for (TreeElement element : _elements) {
            element.expandAll();
        }
    }

    /**
     * Clears the model.
     */
    public void clear() {
        _activeFileFilters.clear();
        _elements.clear();
    }

    /**
     * @return current active background task.
     */
    public List<BackgroundTask> getBackgroundTasks() {
        return _backgroundTasks;
    }

    /**
     *
     * Adds a background
     * task.
     *
     * @param task The task to add.
     */
    public void addBackgroundTask(BackgroundTask task) {
        _backgroundTasks.add(task);
        setChanged();
    }

    /**
     * Removes a background task.
     *
     * @param task The task to remove.
     */
    public void removeBackgroundTask(BackgroundTask task) {
        _backgroundTasks.remove(task);
        setChanged();
    }

    /**
     * This is a getter which gets the text search for the navigator file tree.
     * @return _textSearch the search filter of the navigator file tree.
     */
    public SearchFilter getTextSearch() {
        return _textSearch;
    }

    /**
     * This is a setter which sets the text search for the navigator file tree.
     * @param textSearch The text search of the navigator file tree that should be set.
     */
    public void setTextSearch(SearchFilter textSearch) {
        this._textSearch = textSearch;
        setChanged();
    }
}