Addded sorting logic to pages
This commit is contained in:
parent
da2ba4d9f3
commit
941b4496c2
|
@ -135,12 +135,23 @@ class PageController extends Controller
|
||||||
return redirect($page->getUrl());
|
return redirect($page->getUrl());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Redirect from a special link url which
|
||||||
|
* uses the page id rather than the name.
|
||||||
|
* @param $pageId
|
||||||
|
* @return \Illuminate\Http\RedirectResponse|\Illuminate\Routing\Redirector
|
||||||
|
*/
|
||||||
public function redirectFromLink($pageId)
|
public function redirectFromLink($pageId)
|
||||||
{
|
{
|
||||||
$page = $this->pageRepo->getById($pageId);
|
$page = $this->pageRepo->getById($pageId);
|
||||||
return redirect($page->getUrl());
|
return redirect($page->getUrl());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Search all available pages, Across all books.
|
||||||
|
* @param Request $request
|
||||||
|
* @return \Illuminate\Http\RedirectResponse|\Illuminate\View\View
|
||||||
|
*/
|
||||||
public function searchAll(Request $request)
|
public function searchAll(Request $request)
|
||||||
{
|
{
|
||||||
$searchTerm = $request->get('term');
|
$searchTerm = $request->get('term');
|
||||||
|
@ -150,6 +161,30 @@ class PageController extends Controller
|
||||||
return view('pages/search-results', ['pages' => $pages, 'searchTerm' => $searchTerm]);
|
return view('pages/search-results', ['pages' => $pages, 'searchTerm' => $searchTerm]);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Shows the view which allows pages to be re-ordered and sorted.
|
||||||
|
* @param $bookSlug
|
||||||
|
* @return \Illuminate\View\View
|
||||||
|
*/
|
||||||
|
public function sortPages($bookSlug)
|
||||||
|
{
|
||||||
|
$book = $this->bookRepo->getBySlug($bookSlug);
|
||||||
|
$tree = $this->bookRepo->getTree($book);
|
||||||
|
return view('pages/sort', ['book' => $book, 'tree' => $tree]);
|
||||||
|
}
|
||||||
|
|
||||||
|
public function savePageSort($bookSlug, Request $request)
|
||||||
|
{
|
||||||
|
$book = $this->bookRepo->getBySlug($bookSlug);
|
||||||
|
if(!$request->has('sort-tree')) {
|
||||||
|
return redirect($book->getUrl());
|
||||||
|
}
|
||||||
|
|
||||||
|
$sortMap = json_decode($request->get('sort-tree'));
|
||||||
|
$this->pageRepo->applySortMap($sortMap, $book->id);
|
||||||
|
return redirect($book->getUrl());
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Remove the specified resource from storage.
|
* Remove the specified resource from storage.
|
||||||
*
|
*
|
||||||
|
|
|
@ -24,6 +24,8 @@ Route::group(['prefix' => 'books'], function() {
|
||||||
|
|
||||||
Route::get('/{bookSlug}/page/create', 'PageController@create');
|
Route::get('/{bookSlug}/page/create', 'PageController@create');
|
||||||
Route::post('/{bookSlug}/page', 'PageController@store');
|
Route::post('/{bookSlug}/page', 'PageController@store');
|
||||||
|
Route::get('/{bookSlug}/sort', 'PageController@sortPages');
|
||||||
|
Route::put('/{bookSlug}/sort', 'PageController@savePageSort');
|
||||||
Route::get('/{bookSlug}/{pageSlug}', 'PageController@show');
|
Route::get('/{bookSlug}/{pageSlug}', 'PageController@show');
|
||||||
Route::get('/{bookSlug}/{pageSlug}/create', 'PageController@create');
|
Route::get('/{bookSlug}/{pageSlug}/create', 'PageController@create');
|
||||||
Route::get('/{bookSlug}/{pageSlug}/edit', 'PageController@edit');
|
Route::get('/{bookSlug}/{pageSlug}/edit', 'PageController@edit');
|
||||||
|
|
|
@ -24,7 +24,7 @@ class Page extends Model
|
||||||
|
|
||||||
public function children()
|
public function children()
|
||||||
{
|
{
|
||||||
return $this->hasMany('Oxbow\Page');
|
return $this->hasMany('Oxbow\Page')->orderBy('priority', 'ASC');
|
||||||
}
|
}
|
||||||
|
|
||||||
public function parent()
|
public function parent()
|
||||||
|
|
|
@ -57,6 +57,7 @@ class BookRepo
|
||||||
{
|
{
|
||||||
$tree = $book->toArray();
|
$tree = $book->toArray();
|
||||||
$tree['pages'] = $this->pageRepo->getTreeByBookId($book->id);
|
$tree['pages'] = $this->pageRepo->getTreeByBookId($book->id);
|
||||||
|
$tree['hasChildren'] = count($tree['pages']) > 0;
|
||||||
return $tree;
|
return $tree;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -114,7 +114,24 @@ class PageRepo
|
||||||
*/
|
*/
|
||||||
private function getTopLevelPages($bookId)
|
private function getTopLevelPages($bookId)
|
||||||
{
|
{
|
||||||
return $this->page->where('book_id', '=', $bookId)->where('page_id', '=', 0)->get();
|
return $this->page->where('book_id', '=', $bookId)->where('page_id', '=', 0)->orderBy('priority')->get();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Applies a sort map to all applicable pages.
|
||||||
|
* @param $sortMap
|
||||||
|
* @param $bookId
|
||||||
|
*/
|
||||||
|
public function applySortMap($sortMap, $bookId)
|
||||||
|
{
|
||||||
|
foreach($sortMap as $index => $map) {
|
||||||
|
$page = $this->getById($map->id);
|
||||||
|
if($page->book_id === $bookId) {
|
||||||
|
$page->page_id = $map->parent;
|
||||||
|
$page->priority = $index;
|
||||||
|
$page->save();
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
|
@ -94,6 +94,9 @@ header .menu {
|
||||||
&:hover {
|
&:hover {
|
||||||
opacity: 1;
|
opacity: 1;
|
||||||
}
|
}
|
||||||
|
.buttons a {
|
||||||
|
display: block;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
.page-nav-list {
|
.page-nav-list {
|
||||||
|
@ -268,4 +271,44 @@ h1, h2, h3, h4, h5, h6 {
|
||||||
display: block;
|
display: block;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.sortable-page-list, .sortable-page-list ul {
|
||||||
|
list-style: none;
|
||||||
|
//background-color: rgba(0, 0, 0, 0.04);
|
||||||
|
}
|
||||||
|
.sortable-page-list {
|
||||||
|
margin-left: 0;
|
||||||
|
ul {
|
||||||
|
margin-bottom: 0;
|
||||||
|
margin-top: 0;
|
||||||
|
}
|
||||||
|
li {
|
||||||
|
border-bottom: 1px solid #BBB;
|
||||||
|
border-left: 1px solid #BBB;
|
||||||
|
border-right: 1px solid #BBB;
|
||||||
|
padding: $-xs $-s;
|
||||||
|
}
|
||||||
|
li:first-child {
|
||||||
|
margin-top: $-xs;
|
||||||
|
border-top: 1px solid #BBB;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Jquery Sortable Styles
|
||||||
|
.dragged {
|
||||||
|
position: absolute;
|
||||||
|
opacity: 0.5;
|
||||||
|
z-index: 2000;
|
||||||
|
}
|
||||||
|
|
||||||
|
body.dragging, body.dragging * {
|
||||||
|
cursor: move !important;
|
||||||
|
}
|
||||||
|
|
||||||
|
.sortable-page-list li.placeholder {
|
||||||
|
position: relative;
|
||||||
|
}
|
||||||
|
.sortable-page-list li.placeholder:before {
|
||||||
|
position: absolute;
|
||||||
}
|
}
|
|
@ -8,6 +8,7 @@
|
||||||
<link rel="stylesheet" href="//maxcdn.bootstrapcdn.com/font-awesome/4.3.0/css/font-awesome.min.css">
|
<link rel="stylesheet" href="//maxcdn.bootstrapcdn.com/font-awesome/4.3.0/css/font-awesome.min.css">
|
||||||
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.4/jquery.min.js"></script>
|
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.4/jquery.min.js"></script>
|
||||||
<script src="/bower/bootstrap/dist/js/bootstrap.js"></script>
|
<script src="/bower/bootstrap/dist/js/bootstrap.js"></script>
|
||||||
|
<script src="/bower/jquery-sortable/source/js/jquery-sortable.js"></script>
|
||||||
<script>
|
<script>
|
||||||
$.fn.smoothScrollTo = function() {
|
$.fn.smoothScrollTo = function() {
|
||||||
if(this.length === 0) return;
|
if(this.length === 0) return;
|
||||||
|
|
|
@ -9,6 +9,7 @@
|
||||||
<h4>Book Actions</h4>
|
<h4>Book Actions</h4>
|
||||||
<div class="buttons">
|
<div class="buttons">
|
||||||
<a href="{{$book->getEditUrl()}}"><i class="fa fa-pencil"></i>Edit Book</a>
|
<a href="{{$book->getEditUrl()}}"><i class="fa fa-pencil"></i>Edit Book</a>
|
||||||
|
<a href="{{ $book->getUrl() }}/sort"><i class="fa fa-sort"></i>Sort Pages</a>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,10 @@
|
||||||
|
|
||||||
|
<li data-id="{{$page['id']}}">{{ $page['name'] }}
|
||||||
|
<ul>
|
||||||
|
@if($page['hasChildren'])
|
||||||
|
@foreach($page['pages'] as $childPage)
|
||||||
|
@include('pages/page-tree-sort', ['page'=>$childPage])
|
||||||
|
@endforeach
|
||||||
|
@endif
|
||||||
|
</ul>
|
||||||
|
</li>
|
|
@ -28,10 +28,10 @@
|
||||||
@endif
|
@endif
|
||||||
</div>
|
</div>
|
||||||
<h1>{{$page->name}}</h1>
|
<h1>{{$page->name}}</h1>
|
||||||
@if(count($page->pages) > 0)
|
@if(count($page->children) > 0)
|
||||||
<h4 class="text-muted">Sub-pages</h4>
|
<h4 class="text-muted">Sub-pages</h4>
|
||||||
<div class="page-list">
|
<div class="page-list">
|
||||||
@foreach($page->pages as $childPage)
|
@foreach($page->children as $childPage)
|
||||||
<a href="{{ $childPage->getUrl() }}">{{ $childPage->name }}</a>
|
<a href="{{ $childPage->getUrl() }}">{{ $childPage->name }}</a>
|
||||||
@endforeach
|
@endforeach
|
||||||
</div>
|
</div>
|
||||||
|
|
|
@ -0,0 +1,61 @@
|
||||||
|
@extends('base')
|
||||||
|
|
||||||
|
@section('content')
|
||||||
|
|
||||||
|
<div class="row">
|
||||||
|
<div class="page-menu col-md-3">
|
||||||
|
<div class="page-actions">
|
||||||
|
<form action="{{$book->getUrl()}}/sort" method="POST">
|
||||||
|
{!! csrf_field() !!}
|
||||||
|
<input type="hidden" name="_method" value="PUT">
|
||||||
|
<input type="hidden" id="sort-tree-input" name="sort-tree">
|
||||||
|
<h4>Actions</h4>
|
||||||
|
<div class="list">
|
||||||
|
<button class="button pos" type="submit">Save Ordering</button>
|
||||||
|
</div>
|
||||||
|
</form>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="page-content right col-md-9">
|
||||||
|
<h1>{{ $book->name }} <span class="subheader">Sort Pages</span></h1>
|
||||||
|
|
||||||
|
<ul class="sortable-page-list" id="sort-list">
|
||||||
|
@foreach($tree['pages'] as $treePage)
|
||||||
|
@include('pages/page-tree-sort', ['page' => $treePage])
|
||||||
|
@endforeach
|
||||||
|
</ul>
|
||||||
|
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
$(document).ready(function() {
|
||||||
|
|
||||||
|
var group = $('#sort-list').sortable({
|
||||||
|
group: 'serialization',
|
||||||
|
onDrop: function($item, container, _super) {
|
||||||
|
var data = group.sortable('serialize').get();
|
||||||
|
console.log(data);
|
||||||
|
var pageMap = [];
|
||||||
|
var parent = 0;
|
||||||
|
buildPageMap(pageMap, parent, data[0]);
|
||||||
|
$('#sort-tree-input').val(JSON.stringify(pageMap));
|
||||||
|
_super($item, container);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
function buildPageMap(pageMap, parent, data) {
|
||||||
|
for(var i = 0; i < data.length; i++) {
|
||||||
|
var page = data[i];
|
||||||
|
pageMap.push({
|
||||||
|
id: page.id,
|
||||||
|
parent: parent
|
||||||
|
});
|
||||||
|
buildPageMap(pageMap, page.id, page.children[0]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
});
|
||||||
|
</script>
|
||||||
|
@stop
|
Loading…
Reference in New Issue