Главная
Блог разработчиков phpBB
 
+ 17 предустановленных модов
+ SEO-оптимизация форума
+ авторизация через соц. сети
+ защита от спама

Древовидный список на ASP.NET MVC 4

Anna | 17.06.2014 | нет комментариев

Добрый день! На прогре есть статья, в которой рассказывается как сделать древовидный список. Впрочем, в этой версии будет использован движок Razor, Entity Framework и др., а так же реализованы операции со списком. Данный вариант отличается простотой и быстротой реализации. Статья рассчитана на тех, кто теснее знаком с ASP .NET MVC.

Вероятности:

  • Отображение списка
  • Добавление элементов
  • Перемещение элементов
  • Удаление элементов

Используемые спецтехнологии:

  • Microsoft ASP. NET MVC 4
  • Entity Framework
  • Linq to Entity
  • Microsoft SQL Server (Local DB)

База данных

Так как все записи будут храниться в базе данных, то нужно сделать следующую таблицу:

public class News
{
   public int Id {get;set;} //Идентификатор новости
   public int? ParentId {get;set;} //Идентификатор родительской новости
   public string Title {get;set;} //Заголовок новости
   public bool IsDeleted {get;set;} //Флаг удаления
}

 

Модели

Дальше сотворим модели для работы:
1. Традиционно в моделях не применяют напрямую записи из базы данных, следственно сотворим модель схожую на таблицу.

public class NewsModel
{
   public int Id {get;set;} //Идентификатор новости
   public int? ParentId {get;set;} //Идентификатор родительской новости
   public string Title {get;set;} //Заголовок новости
}

2. Список новостей.

public NewsListModel
{
   public int? Seed {get;set;} //Корневой элемент
   public IEnumerable<NewsModel> News {get;set;} //Список новостей
}

 

Контроллер

Ниже представлен контроллер, тот, что может выбирать, удалять, добавлять и перемещать новости.

public class NewsController : Controller
{
    public ActionResult Index()
    {
        using (NewsContext context = new NewsContext())
        {
            NewsListModel model = new NewsListModel()
            {
                News = context.News.Where(x => !x.IsDeleted).ToArray().Select(x => new NewsModel(x))
            };
            return View(model);
        }
    }

    [HttpPost]
    [ValidateAntiForgeryToken]
    public ActionResult Add(int? parentId, string title)
    {
        using (NewsContext context = new NewsContext())
        {
            var newNews = new News()
            {
                ParentId = parentId,
                Title = title
            };
            context.News.Add(newNews);
            context.SaveChanges();
        }
        return RedirectToAction("Index");
    }

    [ValidateAntiForgeryToken]
    [HttpPost]
    public ActionResult Move(int nodeId, int? newParentId)
    {
        if (nodeId == newParentId)
        {
            return RedirectToAction("Index");
        }
        using (NewsContext context = new NewsContext())
        {
            if (newParentId.HasValue && ContainsChilds(context, nodeId, newParentId.Value))
            {
                return RedirectToAction("Index");
            }
            var node = context.News.Where(x => x.Id == nodeId).Single();
            node.ParentId = newParentId;
            context.SaveChanges();
        }
        return RedirectToAction("Index");
    }

    private bool ContainsChilds(NewsContext context, int parentId, int id)
    {
        bool result = false;
        var inner = context.News.Where(x => x.ParentId == parentId && !x.IsDeleted).ToArray();
        foreach (var node in inner)
        {
            if (node.Id == id && node.ParentId == parentId)
            {
                return true;
            }
            result = ContainsChilds(context, node.Id, id);
        }
        return result;
    }

    [HttpPost]
    public ActionResult Delete(int id)
    {
        using (NewsContext context = new NewsContext())
        {
            DeleteNodes(context, id);
            context.SaveChanges();
        }

        return RedirectToAction("Index");
    }

    private void DeleteNodes(NewsContext context, int id)
    {
        var inner = context.News.Where(x => x.ParentId == id && !x.IsDeleted).ToArray();
        foreach (var node in inner)
        {
            node.IsDeleted = true;
            DeleteNodes(context, node.Id);
        }
        var deleted = context.News.Where(x => x.Id == id && !x.IsDeleted).Single();
        deleted.IsDeleted = true;
    }
}

 

Представление

Как видно из кода, множество способов выполняются рекурсивно. Рекурсия разрешает довольно немногословно реализовать операции. Так же рекурсия применяется при отображении на странице.

 

Источник: programmingmaster.ru

Оставить комментарий
Форум phpBB, русская поддержка форума phpBB
Рейтинг@Mail.ru 2008 - 2017 © BB3x.ru - русская поддержка форума phpBB