You've already forked code_examples_server
mirror of
https://github.com/AdaCore/code_examples_server.git
synced 2026-02-12 12:45:18 -08:00
Replaced custom pagination with django pagination and added jquery waypoints to auto load pages as the user scrolls. Have to add the ability to render and jump to sections of the page.
This commit is contained in:
1
compile_server/app/static/navbar-fixed-left.min.css
vendored
Normal file
1
compile_server/app/static/navbar-fixed-left.min.css
vendored
Normal file
@@ -0,0 +1 @@
|
||||
@media (min-width:768px){.container{width:503px}}@media (min-width:992px){.container{width:723px}}@media (min-width:1200px){.container{width:923px}}@media (min-width:1432px){.container{width:1170px}}body{padding-top:70px;min-height:200vh}.navbar-fixed-left,.navbar-fixed-right{position:fixed;top:0;width:100%;z-index:1030}@media (min-width:768px) and (min-width:768px){.navbar-fixed-left,.navbar-fixed-right{width:232px;height:100vh;border-radius:0}.navbar-fixed-left .container,.navbar-fixed-right .container{padding-right:0;padding-left:0;width:auto}.navbar-fixed-left .navbar-header,.navbar-fixed-right .navbar-header{padding-left:15px;padding-right:15px}.navbar-fixed-left .navbar-collapse,.navbar-fixed-right .navbar-collapse{padding-right:0;padding-left:0;max-height:none}.navbar-fixed-left .navbar-collapse .navbar-nav,.navbar-fixed-right .navbar-collapse .navbar-nav{float:none!important}.navbar-fixed-left .navbar-collapse .navbar-nav>li,.navbar-fixed-right .navbar-collapse .navbar-nav>li{width:100%}.navbar-fixed-left .navbar-collapse .navbar-nav>li.dropdown .dropdown-menu,.navbar-fixed-right .navbar-collapse .navbar-nav>li.dropdown .dropdown-menu{top:0}.navbar-fixed-left .navbar-collapse .navbar-nav.navbar-right,.navbar-fixed-right .navbar-collapse .navbar-nav.navbar-right{margin-right:0}}@media (min-width:768px){body{padding-top:0;padding-left:232px}.navbar-fixed-left{right:auto!important;left:0!important;border-width:0 1px 0 0!important}.navbar-fixed-left .dropdown .dropdown-menu{left:100%;right:auto;border-radius:0 3px 3px 0}.navbar-fixed-left .dropdown .dropdown-toggle .caret{border-top:4px solid transparent;border-left:4px solid;border-bottom:4px solid transparent;border-right:none}}
|
||||
@@ -6,8 +6,13 @@
|
||||
<meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1">
|
||||
<title>Ada for the C Programmer</title>
|
||||
<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/css/bootstrap.min.css" integrity="sha384-BVYiiSIFeK1dGmJRAkycuHAHRg32OmUcww7on3RYdg4Va+PmSTsz/K68vbdEjh4u" crossorigin="anonymous">
|
||||
<link rel="stylesheet" href="{% static "common.css" %}" />
|
||||
<link rel="stylesheet" href="{% static "navbar-fixed-left.min.css" %}" />
|
||||
<link rel="stylesheet" href="{% static "common.css" %}" />
|
||||
<link rel="stylesheet" href="{% static "book_base.css" %}" />
|
||||
|
||||
<script src="{% static "jquery-3.2.1.min.js" %}"></script>
|
||||
<script src="https://cdnjs.cloudflare.com/ajax/libs/waypoints/4.0.1/jquery.waypoints.min.js"></script>
|
||||
<script src="https://cdnjs.cloudflare.com/ajax/libs/waypoints/4.0.1/shortcuts/infinite.min.js"></script>
|
||||
</head>
|
||||
<body>
|
||||
|
||||
@@ -19,11 +24,11 @@
|
||||
</div>
|
||||
|
||||
<script src="{% static "ace-builds/src/ace.js" %}" type="text/javascript" charset="utf-8"></script>
|
||||
<script src="{% static "jquery-3.2.1.min.js" %}"></script>
|
||||
|
||||
<script src="https://cdnjs.cloudflare.com/ajax/libs/popper.js/1.11.0/umd/popper.min.js" integrity="sha384-b/U6ypiBEHpOf/4+1nzFpr53nxSS+GLCkfwBdFNTxtclqqenISfwAzpKaMNFNmj4" crossorigin="anonymous"></script>
|
||||
<script src="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/js/bootstrap.min.js"></script>
|
||||
|
||||
<script src="{% static "editors.js" %}"></script>
|
||||
<script src="{% static "sidebar.js" %}"></script>
|
||||
|
||||
</body>
|
||||
</html>
|
||||
|
||||
@@ -19,7 +19,7 @@
|
||||
</thead>
|
||||
<tbody>
|
||||
{% for b in books %}
|
||||
<tr class='clickable-row' data-href="{{ HTTP_HOST }}/books/{{ b.subpath }}/part1-chapter1">
|
||||
<tr class='clickable-row' data-href="{{ HTTP_HOST }}/books/{{ b.subpath }}">
|
||||
<td>{{ b.title }}</td>
|
||||
<td>{{ b.description }}</td>
|
||||
</tr>
|
||||
|
||||
46
compile_server/app/templates/book_sidebar.html
Normal file
46
compile_server/app/templates/book_sidebar.html
Normal file
@@ -0,0 +1,46 @@
|
||||
{% extends 'book_base.html' %}
|
||||
|
||||
{% block sidebar %}
|
||||
<nav class="navbar navbar-inverse navbar-fixed-left">
|
||||
<div class="container">
|
||||
<div class="navbar-header">
|
||||
<button type="button" class="navbar-toggle collapsed" data-toggle="collapse" data-target="#navbar" aria-expanded="false" aria-controls="navbar">
|
||||
<span class="sr-only">Toggle navigation</span>
|
||||
<span class="icon-bar"></span>
|
||||
<span class="icon-bar"></span>
|
||||
<span class="icon-bar"></span>
|
||||
</button>
|
||||
<h3>{{ book_info.title }}</h3>
|
||||
<a href="{{ HTTP_HOST }}/books/">Back to book list</a>
|
||||
</div>
|
||||
<div id="navbar" class="navbar-collapse collapse">
|
||||
<ul class="nav navbar-nav">
|
||||
{% for p in parts %}
|
||||
{% if forloop.counter == sel_part %}
|
||||
<li class="active">
|
||||
{% else %}
|
||||
<li>
|
||||
{% endif %}
|
||||
<a href="#partSubmenu{{ forloop.counter }}">{{ p.title }}</a>
|
||||
<ul id="partSubmenu{{ forloop.counter }}">
|
||||
{% for c in p.chapters %}
|
||||
{% if forloop.counter == sel_chapter %}
|
||||
<li class="active">
|
||||
{% else %}
|
||||
<li>
|
||||
{% endif %}
|
||||
<a href="{{ HTTP_HOST }}/books/{{ book_info.subpath }}?page={{ c.page }}">{{ c.title }}</a>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="reader_content">
|
||||
{% include "readerpage.html" %}
|
||||
</div>
|
||||
{% endblock%}
|
||||
@@ -1,72 +1,46 @@
|
||||
{% extends 'book_base.html' %}
|
||||
|
||||
{% load markdown_filter %}
|
||||
{% load rst_filter %}
|
||||
|
||||
{% block sidebar %}
|
||||
<nav id="sidebar">
|
||||
<div class="sidebar-header">
|
||||
<h3>{{ book_info.title }}</h3>
|
||||
<a href="{{ HTTP_HOST }}/books/">Back to book list</a>
|
||||
</div>
|
||||
<ul class="list-unstyled components">
|
||||
{% for p in parts %}
|
||||
{% if forloop.counter == sel_part %}
|
||||
<li class="active">
|
||||
{% else %}
|
||||
<li>
|
||||
{% endif %}
|
||||
<a href="#partSubmenu{{ forloop.counter }}" data-toggle="collapse" aria-expanded="false">{{ p.title }}</a>
|
||||
<ul class="collapse list-unstyled" id="partSubmenu{{ forloop.counter }}">
|
||||
{% for c in p.chapters %}
|
||||
{% if forloop.counter == sel_chapter %}
|
||||
<li class="active">
|
||||
{% else %}
|
||||
<li>
|
||||
{% endif %}
|
||||
<a href="{{ HTTP_HOST }}/books/{{ book_info.subpath }}/{{ c.url }}">{{ c.title }}</a>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</nav>
|
||||
{% endblock%}
|
||||
{% block javascript %}
|
||||
<script>
|
||||
$(document).ready(function(){
|
||||
var infinite = new Waypoint.Infinite({
|
||||
element: $('.infinite-container')[0],
|
||||
onBeforePageLoad: function () {
|
||||
$('.loading').show();
|
||||
},
|
||||
onAfterPageLoad: function ($items) {
|
||||
$('.loading').hide();
|
||||
}
|
||||
});
|
||||
});
|
||||
</script>
|
||||
{% endblock %}
|
||||
|
||||
{% block reader %}
|
||||
|
||||
<div id="content">
|
||||
|
||||
<nav class="navbar navbar-default">
|
||||
<div class="container-fluid">
|
||||
<div class="infinite-container">
|
||||
|
||||
<div class="navbar-header">
|
||||
<button type="button" id="sidebarCollapse" class="btn btn-info navbar-btn">
|
||||
<i class="glyphicon glyphicon-align-left"></i>
|
||||
<span></span>
|
||||
</button>
|
||||
{{ sel_topic.title }}
|
||||
</div>
|
||||
|
||||
<div class="collapse navbar-collapse" id="bs-example-navbar-collapse-1">
|
||||
<ul class="nav navbar-nav navbar-right">
|
||||
{% if prev_topic %}
|
||||
<li><a href="{{ HTTP_HOST }}/books/{{ book_info.subpath }}/{{ prev_topic.url }}">Prev - {{ prev_topic.title }}</a></li>
|
||||
{% endif %}
|
||||
{% if next_topic %}
|
||||
<li><a href="{{ HTTP_HOST }}/books/{{ book_info.subpath }}/{{ next_topic.url }}">Next - {{ next_topic.title }}</a></li>
|
||||
{% endif %}
|
||||
</ul>
|
||||
</div>
|
||||
<div class="infinite-item">
|
||||
{% if mdcontent %}
|
||||
{{ mdcontent|markdownify|safe }}
|
||||
{% elif rstcontent %}
|
||||
{{ rstcontent|rstify|safe }}
|
||||
{% endif %}
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
{% if mdcontent %}
|
||||
{{ mdcontent|markdownify|safe }}
|
||||
{% elif rstcontent %}
|
||||
{{ rstcontent|rstify|safe }}
|
||||
{% endif %}
|
||||
</div>
|
||||
|
||||
<div class="loading" style="display: none;">
|
||||
Loading...
|
||||
</div>
|
||||
|
||||
{% if chapter_obj.has_next %}
|
||||
<a class="infinite-more-link" href="{{ HTTP_HOST }}/books/{{ book_info.subpath }}?page={{ chapter_obj.next_page_number }}"></a>
|
||||
{% endif %}
|
||||
|
||||
|
||||
</div>
|
||||
{% endblock%}
|
||||
@@ -11,6 +11,8 @@ import yaml
|
||||
from django.conf import settings
|
||||
|
||||
from django.contrib.auth.models import User, Group
|
||||
from django.core.paginator import Paginator, EmptyPage, PageNotAnInteger
|
||||
|
||||
from django.views.decorators.clickjacking import xframe_options_exempt
|
||||
from rest_framework import viewsets, status
|
||||
from rest_framework.decorators import api_view
|
||||
@@ -117,7 +119,7 @@ def book_list(request):
|
||||
return render(request, 'book_list.html', booklist)
|
||||
|
||||
|
||||
def book_router(request, subpath, part, chapter):
|
||||
def book_router(request, subpath):
|
||||
resources_base_path = os.path.join(settings.RESOURCES_DIR, "books")
|
||||
|
||||
matches = Book.objects.filter(subpath=subpath)
|
||||
@@ -143,52 +145,44 @@ def book_router(request, subpath, part, chapter):
|
||||
htmldata = bookdata
|
||||
htmldata['book_info'] = book
|
||||
|
||||
# store chapter and part numbers for absolute links
|
||||
htmldata['sel_part'] = int(part)
|
||||
htmldata['sel_chapter'] = int(chapter)
|
||||
|
||||
# strip chapters out of list into new list for prev, next references
|
||||
chapter_list = []
|
||||
for p in bookdata['parts']:
|
||||
chapter_list.extend(p['chapters'])
|
||||
|
||||
# search list for current, prev, and next chapter references
|
||||
val_search = "part%s-chapter%s" % (part, chapter)
|
||||
paginator = Paginator(chapter_list, 1)
|
||||
page = request.GET.get('page', 1)
|
||||
|
||||
inrange = False
|
||||
for i, ch in enumerate(chapter_list):
|
||||
if ch['url'] == val_search:
|
||||
inrange = True
|
||||
htmldata['sel_topic'] = ch
|
||||
if i != 0:
|
||||
htmldata['prev_topic'] = chapter_list[i - 1]
|
||||
if i != len(chapter_list) - 1:
|
||||
htmldata['next_topic'] = chapter_list[i + 1]
|
||||
break
|
||||
try:
|
||||
chapter_obj = paginator.page(page)
|
||||
except PageNotAnInteger:
|
||||
# If page is not an integer, deliver first page.
|
||||
chapter_obj = paginator.page(1)
|
||||
except EmptyPage:
|
||||
# If page is out of range (e.g. 9999), deliver last page of results.
|
||||
chapter_obj = paginator.page(paginator.num_pages)
|
||||
|
||||
# load page, if part or chapter is out of range go to unknown page link
|
||||
if inrange:
|
||||
mdcontent_page = os.path.join(book['directory'],
|
||||
"pages",
|
||||
"part%s-chapter%s.md" % (part, chapter))
|
||||
rstcontent_page = os.path.join(book['directory'],
|
||||
"pages",
|
||||
"part%s-chapter%s.rst" % (part, chapter))
|
||||
htmldata['chapter_obj'] = chapter_obj
|
||||
|
||||
# check for markdown version
|
||||
if os.path.isfile(mdcontent_page):
|
||||
with open(mdcontent_page, 'r') as f:
|
||||
htmldata['mdcontent'] = f.read()
|
||||
elif os.path.isfile(rstcontent_page):
|
||||
with open(rstcontent_page, 'r') as f:
|
||||
htmldata['rstcontent'] = f.read()
|
||||
else:
|
||||
with open(os.path.join(resources_base_path,
|
||||
"under-construction.md")) as f:
|
||||
htmldata['mdcontent'] = f.read()
|
||||
chapter = chapter_obj.object_list[0]
|
||||
|
||||
mdcontent_page = os.path.join(book['directory'],
|
||||
"pages",
|
||||
"%s.md" % (chapter["url"]))
|
||||
rstcontent_page = os.path.join(book['directory'],
|
||||
"pages",
|
||||
"%s.rst" % (chapter["url"]))
|
||||
|
||||
# check for markdown version
|
||||
if os.path.isfile(mdcontent_page):
|
||||
with open(mdcontent_page, 'r') as f:
|
||||
htmldata['mdcontent'] = f.read()
|
||||
elif os.path.isfile(rstcontent_page):
|
||||
with open(rstcontent_page, 'r') as f:
|
||||
htmldata['rstcontent'] = f.read()
|
||||
else:
|
||||
with open(os.path.join(resources_base_path,
|
||||
"invalid-page.md")) as f:
|
||||
"under-construction.md")) as f:
|
||||
htmldata['mdcontent'] = f.read()
|
||||
|
||||
return render(request, 'readerpage.html', htmldata)
|
||||
return render(request, 'book_sidebar.html', htmldata)
|
||||
|
||||
@@ -56,7 +56,7 @@ urlpatterns = [
|
||||
url(r'^examples_list/', views.examples_list),
|
||||
|
||||
# URL router for Books
|
||||
url(r'^books/(.+)/part(\d+)-chapter(\d+)', views.book_router),
|
||||
url(r'^books/(.+)', views.book_router),
|
||||
|
||||
# URL router for Book landing
|
||||
url(r'^books', views.book_list),
|
||||
|
||||
@@ -6,13 +6,17 @@ parts:
|
||||
chapters:
|
||||
- title: "Chapter 1"
|
||||
url: "part1-chapter1"
|
||||
page: 1
|
||||
- title: "Chapter 2"
|
||||
url: "part1-chapter2"
|
||||
page: 2
|
||||
- title: "Part 2"
|
||||
chapters:
|
||||
- title: "Chapter 1"
|
||||
url: "part2-chapter1"
|
||||
page: 3
|
||||
- title: "Chapter 2"
|
||||
url: "part2-chapter2"
|
||||
page: 4
|
||||
...
|
||||
|
||||
|
||||
@@ -6,7 +6,7 @@ Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nullam id massa felis.
|
||||
### Test
|
||||
This is a test of inserting code blocks in the markdown
|
||||
|
||||
<div example_editor="Hello World"></div>
|
||||
<div example_editor="Hello world runnable example"></div>
|
||||
|
||||
Fusce molestie commodo nisi, bibendum dictum purus vehicula vel. Nulla mattis lobortis ipsum ac ornare. Integer sed erat vel mauris volutpat sodales nec auctor nulla. Aliquam ac adipiscing erat. Aliquam erat volutpat. Aenean fringilla congue odio non mattis. Pellentesque habitant morbi tristique senectus et netus et malesuada fames ac turpis egestas. Quisque porta vehicula diam, et placerat eros iaculis et. Cras nec ante ipsum, eu cursus sem. Suspendisse nec orci neque, ac egestas sapien.
|
||||
|
||||
@@ -14,4 +14,6 @@ Pellentesque augue neque, bibendum eu elementum non, aliquam non nunc. Sed eget
|
||||
|
||||
Mauris et eros erat, elementum iaculis velit. Donec nec quam felis, sed consequat velit. Nam dolor velit, bibendum vitae convallis id, semper sit amet diam. Integer auctor ultrices metus luctus mattis. Nulla sagittis suscipit arcu, et consequat ipsum dignissim eu. Nulla laoreet libero eget erat fermentum id porttitor odio blandit. Vestibulum ante ipsum primis in faucibus orci luctus et ultrices posuere cubilia Curae; Nullam eget nunc eget tortor pretium sodales. Curabitur dapibus tristique lorem nec dignissim. Nullam pretium laoreet arcu ut semper. Nam ac risus et lacus auctor tempor. Curabitur bibendum, est tristique fermentum mattis, quam libero rutrum enim, at interdum dolor nisi ac nisi. Morbi ac tellus sem. In ornare vehicula risus sit amet venenatis. Pellentesque magna tellus, suscipit ac dapibus ut, rhoncus nec ante. Nullam ac purus eu massa vestibulum luctus a sed erat.
|
||||
|
||||
Nam lobortis aliquam scelerisque. Lorem ipsum dolor sit amet, consectetur adipiscing elit. Fusce auctor nisl feugiat nunc iaculis malesuada. Vestibulum neque nunc, adipiscing lacinia vehicula ut, blandit at diam. Pellentesque lobortis, justo non sollicitudin vestibulum, est tortor mattis sem, at pulvinar ante felis non ligula. Integer consequat congue adipiscing. Proin ut sodales nunc. Ut eleifend venenatis aliquam. Phasellus et viverra mauris. Quisque commodo sodales feugiat. Proin dignissim mollis quam, vel tristique velit sodales in. Aliquam egestas euismod venenatis.
|
||||
Nam lobortis aliquam scelerisque. Lorem ipsum dolor sit amet, consectetur adipiscing elit. Fusce auctor nisl feugiat nunc iaculis malesuada. Vestibulum neque nunc, adipiscing lacinia vehicula ut, blandit at diam. Pellentesque lobortis, justo non sollicitudin vestibulum, est tortor mattis sem, at pulvinar ante felis non ligula. Integer consequat congue adipiscing. Proin ut sodales nunc. Ut eleifend venenatis aliquam. Phasellus et viverra mauris. Quisque commodo sodales feugiat. Proin dignissim mollis quam, vel tristique velit sodales in. Aliquam egestas euismod venenatis.
|
||||
|
||||
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nullam id massa felis. Nam eget risus sit amet ante tempor lacinia. Mauris ut nunc sem. Cras mattis, nibh quis fermentum porttitor, arcu tortor porttitor magna, ac adipiscing quam urna at lectus. Ut at dolor in elit tempor ultrices sagittis sed lacus. Nullam a lectus mauris. Pellentesque molestie, leo in auctor semper, magna sem mattis tellus, a consectetur nisl tellus volutpat quam. Etiam ultricies risus sed sapien convallis aliquet. Curabitur vehicula purus vitae justo commodo facilisis. Quisque at porta ipsum. Sed purus leo, mattis sed ultricies ac, ultricies eget lacus. Sed ac nibh est. Suspendisse sed orci nisl. Vestibulum ultrices metus sapien, sed interdum nunc. In arcu neque, sollicitudin ut porta eu, viverra at elit. Nam accumsan condimentum metus nec accumsan. Nunc porta consectetur nisi in ornare. Vestibulum tempor mollis dui quis luctus. Aliquam dolor enim, tristique a blandit eu, auctor ut odio.
|
||||
@@ -10,7 +10,7 @@ This is a test of inserting code blocks in the RST
|
||||
|
||||
.. raw:: html
|
||||
|
||||
<div example_editor="Hello World">
|
||||
<div example_editor="Hello world runnable example">
|
||||
|
||||
.. raw:: html
|
||||
|
||||
|
||||
Reference in New Issue
Block a user