Commit 297aee23 authored by Liam Brenner's avatar Liam Brenner
Browse files

WIP

parent 29c5409c
{% extends "wagtailadmin/base.html" %}
{% load wagtailimages_tags staticfiles i18n %}
{% block titletag %}{% blocktrans with title=image.title %}Editing image {{ title }}{% endblocktrans %}{% endblock %}
{% block extra_css %}
{{ block.super }}
<!-- Focal point chooser -->
<link rel="stylesheet" href="{% static 'wagtailimages/css/vendor/jquery.Jcrop.min.css' %}" type="text/css">
<link rel="stylesheet" href="{% static 'wagtailimages/css/focal-point-chooser.css' %}" type="text/css">
{% endblock %}
{% block extra_js %}
{{ block.super }}
{% url 'wagtailadmin_tag_autocomplete' as autocomplete_url %}
<script>
$(function() {
$('#id_tags').tagit({
autocomplete: {source: "{{ autocomplete_url|addslashes }}"}
});
});
</script>
<!-- Focal point chooser -->
<script src="{% static 'wagtailadmin/js/vendor/jquery.ba-throttle-debounce.min.js' %}"></script>
<script src="{% static 'wagtailimages/js/vendor/jquery.Jcrop.min.js' %}"></script>
<script src="{% static 'wagtailimages/js/focal-point-chooser.js' %}"></script>
{% endblock %}
{% block content %}
{% trans "Editing" as editing_str %}
{% include "wagtailadmin/shared/header.html" with title=editing_str subtitle=image.title icon="image" usage_object=image %}
<div class="row row-flush nice-padding">
<div class="col5">
<form action="{% url 'wagtailimages:edit' image.id %}" method="POST" enctype="multipart/form-data">
{% csrf_token %}
<ul class="fields">
{% for field in form %}
{% if field.name == 'file' %}
{% include "wagtailimages/images/_file_field_as_li.html" %}
{% elif field.is_hidden %}
{{ field }}
{% else %}
{% include "wagtailadmin/shared/field_as_li.html" %}
{% endif %}
{% endfor %}
<li>
<input type="submit" value="{% trans 'Save' %}" />
{% if user_can_delete %}
<a href="{% url 'wagtailimages:delete' image.id %}" class="button button-secondary no">{% trans "Delete image" %}</a>
{% endif %}
</li>
</ul>
</form>
</div>
<div class="col5 divider-after">
<h2 class="label">{% trans "Focal point (optional)" %}</h2>
<p>{% trans "To define this image's most important region, drag a box over the image below." %} {% if image.focal_point %}({% trans "Current focal point shown" %}){% endif %}</p>
{% image image max-800x600 as rendition %}
<div class="focal-point-chooser"
style="max-width: {{ rendition.width }}px; max-height: {{ rendition.height }}px;"
data-focal-point-x="{{ image.focal_point_x }}"
data-focal-point-y="{{ image.focal_point_y }}"
data-focal-point-width="{{ image.focal_point_width }}"
data-focal-point-height="{{ image.focal_point_height }}">
<img {{ rendition.attrs }} data-original-width="{{ image.width }}" data-original-height="{{ image.height }}" class="show-transparency">
<div class="current-focal-point-indicator{% if not image.focal_point %} hidden{% endif %}"></div>
</div>
</div>
<div class="col2 ">
{% if url_generator_enabled %}
<a href="{% url 'wagtailimages:url_generator' image.id %}" class="button bicolor icon icon-link">{% trans "URL Generator" %}</a>
<hr />
{% endif %}
{% image image original as original_image %}
<dl>
<dt>{% trans "Max dimensions" %}</dt>
<dd>{{ original_image.width }}x{{ original_image.height }}</dd>
<dt>{% trans "Filesize" %}</dt>
<dd>{% if filesize %}{{ filesize|filesizeformat }}{% else %}{% trans "File not found" %}{% endif %}</dd>
</dl>
</div>
</div>
{% endblock %}
{% extends "wagtailadmin/base.html" %}
{% load i18n %}
{% block titletag %}{% trans "Videos" %}{% endblock %}
{% block extra_js %}
{{ block.super }}
<script>
window.headerSearch = {
url: "{% url 'wagtailvideos:index' %}",
termInput: "#id_q",
targetOutput: "#video-results"
}
$(function() {
$('#collection_chooser_collection_id').change(function() {
this.form.submit();
})
});
</script>
{% endblock %}
{% block content %}
{% trans "Videos" as im_str %}
{% trans "Add a video" as add_img_str %}
{% include "wagtailadmin/shared/header.html" with title=img_str add_link="wagtailvideos:add_multiple" icon="video" add_text=add_img_str search_url="wagtailvideos:index" %}
<div class="nice-padding">
{% if collections %}
<form class="image-search search-bar" action="{% url 'wagtailvideos:index' %}" method="GET">
<ul class="fields">
{% include "wagtailadmin/shared/collection_chooser.html" %}
</ul>
</form>
{% endif %}
<div id="image-results">
{% include "wagtailvideos/videos/results.html" %}
</div>
</div>
{% endblock %}
{% load wagtailadmin_tags %}
{% load i18n %}
{% if images %}
{% if is_searching %}
<h2>
{% blocktrans count counter=images.paginator.count %}
There is one match
{% plural %}
There are {{ counter }} matches
{% endblocktrans %}
</h2>
{% search_other %}
{% else %}
<h2>{% trans "Latest videos" %}</h2>
{% endif %}
<ul class="listing horiz images">
{% for image in images %}
<li>
<a class="image-choice" href="{% url 'wagtailimages:edit' image.id %}">
{% include "wagtailvideos/videos/results_image.html" %}
<h3>{{ image.title|ellipsistrim:60 }}</h3>
</a>
</li>
{% endfor %}
</ul>
{% include "wagtailadmin/shared/pagination_nav.html" with items=images is_searching=is_searching query_string=query_string linkurl="wagtailimages:index" %}
{% else %}
{% if is_searching %}
<h2>{% blocktrans %}Sorry, no videos match "<em>{{ query_string }}</em>"{% endblocktrans %}</h2>
{% search_other %}
{% else %}
{% url 'wagtailimages:add_multiple' as wagtailimages_add_image_url %}
{% if current_collection %}
<p>{% blocktrans %}You've not uploaded any videos in this collection. Why not <a href="{{ wagtailimages_add_image_url }}">add one now</a>?{% endblocktrans %}</p>
{% else %}
<p>{% blocktrans %}You've not uploaded any videos. Why not <a href="{{ wagtailimages_add_image_url }}">add one now</a>?{% endblocktrans %}</p>
{% endif %}
{% endif %}
{% endif %}
{% comment %}
Separated out of results.html to prevent invalid images from crashing the entire
images listing. (issue #1805)
If an error is raised inside a template include, the error is caught by the
calling {% include %} tag and the contents blanked out.
This behaviour caused a confusing error on the images listing view where it
would go blank if one of the images was invalid.
Separating the image rendering code into this file allows us to limit Django's
crash/blanking behaviour to a single image so the listing can still be used when
the issue occurs.
{% endcomment %}
<div class="image"><img src='{{image.thumbnail.url}}' height=165 width=165 class="show-transparency" /></img></div>
{% extends "wagtailadmin/base.html" %}
{% load wagtailimages_tags staticfiles i18n %}
{% block titletag %}{% blocktrans with title=image.title %}Editing image {{ title }}{% endblocktrans %}{% endblock %}
{% block content %}
{% trans "Generating URL" as title_str %}
{% include "wagtailadmin/shared/header.html" with title=title_str subtitle=image.title icon="image" %}
<div class="image-url-generator nice-padding" data-generator-url="{% url 'wagtailimages:generate_url' image.id '__filterspec__' %}">
<form>
<ul class="fields">
{% include "wagtailadmin/shared/field_as_li.html" with field=form.filter_method %}
<li>
<ul class="field-row">
{% include "wagtailadmin/shared/field_as_li.html" with field=form.width li_classes="field-col col4" %}
{% include "wagtailadmin/shared/field_as_li.html" with field=form.height li_classes="field-col col4" %}
{% include "wagtailadmin/shared/field_as_li.html" with field=form.closeness li_classes="field-col col4" %}
</ul>
</li>
</ul>
</form>
<h2 class="icon icon-link">{% trans "URL" %}</h2>
<textarea id="result-url" rows="1"></textarea>
<h2 class="icon icon-view">{% trans "Preview" %}</h2>
<div>
<div class="loading-mask inline-block">
<img class="preview" src="" alt="Preview" />
</div>
</div>
<p id="note-size" class="help-block help-warning">{% trans "Note that images generated larger than the screen will appear smaller when previewed here, so they fit the screen." %}</p>
</div>
{% endblock %}
{% block extra_js %}
{{ block.super }}
<script src="{% static 'wagtailadmin/js/vendor/jquery.ba-throttle-debounce.min.js' %}"></script>
<script src="{% static 'wagtailimages/js/image-url-generator.js' %}"></script>
{% endblock %}
{% extends "wagtailadmin/base.html" %}
{% load i18n %}
{% block titletag %}{% blocktrans with title=image.title %}Usage of {{ title }}{% endblocktrans %}{% endblock %}
{% block content %}
{% trans "Usage of" as usage_str %}
{% include "wagtailadmin/shared/header.html" with title=usage_str subtitle=image.title %}
<div class="nice-padding">
<table class="listing">
<col />
<col width="30%"/>
<col width="15%"/>
<col width="15%"/>
<thead>
<tr>
<th class="title">{% trans "Title" %}</th>
<th>{% trans "Parent" %}</th>
<th>{% trans "Type" %}</th>
<th>{% trans "Status" %}</th>
</tr>
</thead>
<tbody>
{% for page in used_by %}
<tr>
<td class="title" valign="top">
<h2><a href="{% url 'wagtailadmin_pages:edit' page.id %}" title="{% trans 'Edit this page' %}">{{ page.title }}</a></h2>
</td>
<td>
{% if page.get_parent %}
<a href="{% url 'wagtailadmin_explore' page.get_parent.id %}">{{ page.get_parent.title }}</a>
{% endif %}
</td>
<td>
{{ page.content_type.model_class.get_verbose_name }}
</td>
<td>
{% include "wagtailadmin/shared/page_status_tag.html" with page=page %}
</td>
</tr>
{% endfor %}
</tbody>
</table>
</div>
{% include "wagtailadmin/shared/pagination_nav.html" with items=used_by linkurl="-" %}
{% endblock %}
{% extends "wagtailadmin/widgets/chooser.html" %}
{% load wagtailimages_tags %}
{% block chooser_class %}image-chooser{% endblock %}
{% block chosen_state_view %}
<div class="preview-image">
{% if image %}
{% image image max-165x165 class="show-transparency" %}
{% else %}
<img>
{% endif %}
</div>
{% endblock %}
{% block edit_chosen_item_url %}{% if image %}{% url 'wagtailimages:edit' image.id %}{% endif %}{% endblock %}
from django.conf.urls import url
from wagtailvideos.views import chooser, multiple, videos
urlpatterns = [
url(r'^$', videos.index, name='index'),
url(r'^(\d+)/$', videos.edit, name='edit'),
url(r'^(\d+)/delete/$', videos.delete, name='delete'),
url(r'^(\d+)/generate_url/$', videos.url_generator, name='url_generator'),
url(r'^(\d+)/generate_url/(.*)/$', videos.generate_url, name='generate_url'),
#url(r'^(\d+)/preview/(.*)/$', videos.preview, name='preview'),
url(r'^add/$', videos.add, name='add'),
url(r'^usage/(\d+)/$', videos.usage, name='video_usage'),
url(r'^multiple/add/$', multiple.add, name='add_multiple'),
url(r'^multiple/(\d+)/$', multiple.edit, name='edit_multiple'),
url(r'^multiple/(\d+)/delete/$', multiple.delete, name='delete_multiple'),
url(r'^chooser/$', chooser.chooser, name='chooser'),
url(r'^chooser/(\d+)/$', chooser.video_chosen, name='video_chosen'),
url(r'^chooser/upload/$', chooser.chooser_upload, name='chooser_upload'),
url(r'^chooser/(\d+)/select_format/$', chooser.chooser_select_format, name='chooser_select_format'),
]
try:
from shutil import which
except ImportError:
from distutils.spawn import find_executable as which
import json
from django.core.urlresolvers import reverse
from django.shortcuts import get_object_or_404, render
from wagtail.utils.pagination import paginate
from wagtail.wagtailadmin.forms import SearchForm
from wagtail.wagtailadmin.modal_workflow import render_modal_workflow
from wagtail.wagtailcore.models import Collection
from wagtail.wagtailsearch.backends import get_search_backends
from wagtailvideos.formats import get_video_format
from wagtailvideos.forms import VideoInsertionForm, get_video_form
from wagtailvideos.models import get_video_model
def get_video_json(image):
"""
helper function: given an image, return the json to pass back to the
image chooser panel
"""
preview_image = image.get_rendition('max-165x165')
return json.dumps({
'id': image.id,
'edit_link': reverse('wagtailimages:edit', args=(image.id,)),
'title': image.title,
'preview': {
'url': preview_image.url,
'width': preview_image.width,
'height': preview_image.height,
}
})
def chooser(request):
Video = get_video_model()
VideoForm = get_video_form(Video)
uploadform = VideoForm()
videos = Video.objects.order_by('-created_at')
q = None
if (
'q' in request.GET or 'p' in request.GET or 'tag' in request.GET or
'collection_id' in request.GET
):
# this request is triggered from search, pagination or 'popular tags';
# we will just render the results.html fragment
collection_id = request.GET.get('collection_id')
if collection_id:
videos = videos.filter(collection=collection_id)
searchform = SearchForm(request.GET)
if searchform.is_valid():
q = searchform.cleaned_data['q']
videos = videos.search(q)
is_searching = True
else:
is_searching = False
tag_name = request.GET.get('tag')
if tag_name:
videos = videos.filter(tags__name=tag_name)
# Pagination
paginator, videos = paginate(request, videos, per_page=12)
return render(request, "wagtailvideos/chooser/results.html", {
'videos': videos,
'is_searching': is_searching,
'query_string': q,
'will_select_format': request.GET.get('select_format')
})
else:
searchform = SearchForm()
collections = Collection.objects.all()
if len(collections) < 2:
collections = None
paginator, videos = paginate(request, videos, per_page=12)
return render_modal_workflow(request, 'wagtailvideos/chooser/chooser.html', 'wagtailvideos/chooser/chooser.js', {
'videos': videos,
'uploadform': uploadform,
'searchform': searchform,
'is_searching': False,
'query_string': q,
'will_select_format': request.GET.get('select_format'),
'popular_tags': Video.popular_tags(),
'collections': collections,
})
def video_chosen(request, video_id):
video = get_object_or_404(get_video_model(), id=video_id)
return render_modal_workflow(
request, None, 'wagtailvideos/chooser/image_chosen.js',
{'video_json': get_video_json(video)}
)
def chooser_upload(request):
Video = get_video_model()
VideoForm = get_video_form(Video)
searchform = SearchForm()
if request.POST:
video = Video(uploaded_by_user=request.user)
form = VideoForm(request.POST, request.FILES, instance=video)
if form.is_valid():
form.save()
# Reindex the video to make sure all tags are indexed
for backend in get_search_backends():
backend.add(video)
if request.GET.get('select_format'):
form = VideoInsertionForm(initial={'alt_text': video.default_alt_text})
return render_modal_workflow(
request, 'wagtailvideos/chooser/select_format.html', 'wagtailvideos/chooser/select_format.js',
{'video': video, 'form': form}
)
else:
# not specifying a format; return the video details now
return render_modal_workflow(
request, None, 'wagtailvideos/chooser/videos_chosen.js',
{'video_json': get_video_json(video)}
)
else:
form = VideoForm()
videos = Video.objects.order_by('title')
return render_modal_workflow(
request, 'wagtailvideos/chooser/chooser.html', 'wagtailvideos/chooser/chooser.js',
{'videos': videos, 'uploadform': form, 'searchform': searchform}
)
def chooser_select_format(request, video_id):
video = get_object_or_404(get_video_model(), id=video_id)
if request.POST:
form = VideoInsertionForm(request.POST, initial={'alt_text': video.default_alt_text})
if form.is_valid():
format = get_video_format(form.cleaned_data['format'])
preview_video = video.get_rendition(format.filter_spec)
video_json = json.dumps({
'id': image.id,
'title': image.title,
'format': format.name,
'alt': form.cleaned_data['alt_text'],
'class': format.classnames,
'edit_link': reverse('wagtailvideos:edit', args=(video.id,)),
'preview': {
'url': preview_image.url,
'width': preview_image.width,
'height': preview_image.height,
},
'html': format.image_to_editor_html(image, form.cleaned_data['alt_text']),
})
return render_modal_workflow(
request, None, 'wagtailimages/chooser/image_chosen.js',
{'image_json': image_json}
)
else:
form = ImageInsertionForm(initial={'alt_text': image.default_alt_text})
return render_modal_workflow(
request, 'wagtailimages/chooser/select_format.html', 'wagtailimages/chooser/select_format.js',
{'image': image, 'form': form}
)
from wsgiref.util import FileWrapper
import imghdr
from django.shortcuts import get_object_or_404
from django.http import HttpResponse, StreamingHttpResponse
from django.core.exceptions import PermissionDenied
from wagtail.wagtailimages.models import get_image_model
from wagtail.wagtailimages.utils import verify_signature
from wagtail.wagtailimages.exceptions import InvalidFilterSpecError
def serve(request, signature, image_id, filter_spec):
image = get_object_or_404(get_image_model(), id=image_id)
if not verify_signature(signature.encode(), image_id, filter_spec):
raise PermissionDenied
try:
rendition = image.get_rendition(filter_spec)
rendition.file.open('rb')
image_format = imghdr.what(rendition.file)
return StreamingHttpResponse(FileWrapper(rendition.file), content_type='image/' + image_format)
except InvalidFilterSpecError:
return HttpResponse("Invalid filter spec: " + filter_spec, content_type='text/plain', status=400)
from django.http import HttpResponseBadRequest, JsonResponse
from django.shortcuts import get_object_or_404, render
from django.template.loader import render_to_string
from django.utils.encoding import force_text
from django.views.decorators.http import require_POST
from django.views.decorators.vary import vary_on_headers
from wagtail.wagtailadmin.utils import PermissionPolicyChecker
from wagtail.wagtailsearch.backends import get_search_backends
from wagtailvideos.fields import ALLOWED_EXTENSIONS
from wagtailvideos.forms import get_video_form
from wagtailvideos.models import get_video_model
from wagtailvideos.permissions import permission_policy
permission_checker = PermissionPolicyChecker(permission_policy)
def get_video_edit_form(VideoModel):
VideoForm = get_video_form(VideoModel)
# Make a new form with the file and focal point fields excluded
class VideoEditForm(VideoForm):
class Meta(VideoForm.Meta):
model = VideoModel
exclude = (
'file',
)
return VideoEditForm
@vary_on_headers('X-Requested-With')
def add(request):
Video = get_video_model()
VideoForm = get_video_form(Video)
collections = permission_policy.collections_user_has_permission_for(request.user, 'add')
if len(collections) > 1:
collections_to_choose = collections
else:
# no need to show a collections chooser
collections_to_choose = None
if request.method == 'POST':
if not request.is_ajax():
return HttpResponseBadRequest("Cannot POST to this view without AJAX")
if not request.FILES:
return HttpResponseBadRequest("Must upload a file")
# Build a form for validation
form = VideoForm({
'title': request.FILES['files[]'].name,
'collection': request.POST.get('collection'),
}, {
'file': request.FILES['files[]'],
})
if form.is_valid():
# Save
video = form.save(commit=False)
video.uploaded_by_user = request.user
video.file_size = video.file.size
video.save()
# Success! Send back an edit form for this image to the user
return JsonResponse({
'success': True,
'video_id': int(video.id),
'form': render_to_string('wagtailvideos/multiple/edit_form.html', {
'video': video,
'form': get_video_edit_form(Video)(
instance=video, prefix='image-%d' % video.id),
}, request=request),
})
else:
print(form.errors)
# Validation error
return JsonResponse({
'success': False,
# https://github.com/django/django/blob/stable/1.6.x/django/forms/util.py#L45
'error_message': '\n'.join(['\n'.join([force_text(i) for i in v]) for k, v in form.errors.items()]),
})
else:
form = VideoForm()
return render(request, 'wagtailvideos/multiple/add.html', {
'max_filesize': form.fields['file'].max_upload_size,
'help_text': form.fields['file'].help_text,
'allowed_extensions': ALLOWED_EXTENSIONS,
'error_max_file_size': form.fields['file'].error_messages['file_too_large_unknown_size'],
'error_accepted_file_types': form.fields['file'].error_messages['invalid_image'],
'collections': collections_to_choose,
})
@require_POST
def edit(request, video_id, callback=None):
Video = get_video_model()
VideoForm = get_video_edit_form(Video)
video = get_object_or_404(Video, id=video_id)
if not request.is_ajax():
return HttpResponseBadRequest("Cannot POST to this view without AJAX")
form = VideoForm(
request.POST, request.FILES, instance=video, prefix='video-' + video_id
)
if form.is_valid():
form.save()
# Reindex the image to make sure all tags are indexed
for backend in get_search_backends():
backend.add(video)
return JsonResponse({
'success': True,
'video_id': int(video_id),
})
else:
return JsonResponse({
'success': False,
'video_id': int(video_id),
'form': render_to_string('wagtailvideos/multiple/edit_form.html', {
'video': video,
'form': form,
}, request=request),
})
@require_POST
def delete(request, video_id):
video = get_object_or_404(get_video_model(), id=video_id)
if not request.is_ajax():
return HttpResponseBadRequest("Cannot POST to this view without AJAX")
video.delete()
return JsonResponse({
'success': True,
'video_id': int(video_id),
})
import os
from django.core.urlresolvers import NoReverseMatch, reverse
from django.http import JsonResponse
from django.shortcuts import get_object_or_404, redirect, render
from django.utils.translation import ugettext as _
from django.views.decorators.vary import vary_on_headers
from wagtail.utils.pagination import paginate
from wagtail.wagtailadmin import messages
from wagtail.wagtailadmin.forms import SearchForm
from wagtail.wagtailcore.models import Collection, Site
from wagtail.wagtailsearch.backends import get_search_backends
from wagtailvideos.forms import URLGeneratorForm, get_video_form
from wagtailvideos.models import get_video_model
@vary_on_headers('X-Requested-With')
def index(request):
Video = get_video_model()
# Get images (filtered by user permission)
videos = Video.objects.all()
# Search
query_string = None
if 'q' in request.GET:
form = SearchForm(request.GET, placeholder=_("Search videos"))
if form.is_valid():
query_string = form.cleaned_data['q']
videos = videos.search(query_string)
else:
form = SearchForm(placeholder=_("Search videos"))
# Filter by collection
current_collection = None
collection_id = request.GET.get('collection_id')
if collection_id:
try:
current_collection = Collection.objects.get(id=collection_id)
videos = videos.filter(collection=current_collection)
except (ValueError, Collection.DoesNotExist):
pass
paginator, videos = paginate(request, videos)
# Create response
if request.is_ajax():
return render(request, 'wagtailvideos/videos/results.html', {
'vidoes': videos,
'query_string': query_string,
'is_searching': bool(query_string),
})
else:
return render(request, 'wagtailvideos/videos/index.html', {
'images': videos,
'query_string': query_string,
'is_searching': bool(query_string),
'search_form': form,
'popular_tags': Video.popular_tags(),
'current_collection': current_collection,
})
def edit(request, image_id):
Image = get_video_model()
ImageForm = get_video_form(Image)
image = get_object_or_404(Image, id=image_id)
if request.POST:
original_file = image.file
form = ImageForm(request.POST, request.FILES, instance=image, user=request.user)
if form.is_valid():
if 'file' in form.changed_data:
# if providing a new image file, delete the old one and all renditions.
# NB Doing this via original_file.delete() clears the file field,
# which definitely isn't what we want...
original_file.storage.delete(original_file.name)
image.renditions.all().delete()
# Set new image file size
image.file_size = image.file.size
form.save()
# Reindex the image to make sure all tags are indexed
for backend in get_search_backends():
backend.add(image)
messages.success(request, _("Image '{0}' updated.").format(image.title), buttons=[
messages.button(reverse('wagtailvideos:edit', args=(image.id,)), _('Edit again'))
])
return redirect('wagtailvideos:index')
else:
messages.error(request, _("The image could not be saved due to errors."))
else:
form = ImageForm(instance=image, user=request.user)
# Check if we should enable the frontend url generator
try:
reverse('wagtailvideos_serve', args=('foo', '1', 'bar'))
url_generator_enabled = True
except NoReverseMatch:
url_generator_enabled = False
if image.is_stored_locally():
# Give error if image file doesn't exist
if not os.path.isfile(image.file.path):
messages.error(request, _(
"The source image file could not be found. Please change the source or delete the image."
).format(image.title), buttons=[
messages.button(reverse('wagtailvideos:delete', args=(image.id,)), _('Delete'))
])
return render(request, "wagtailvideos/images/edit.html", {
'image': image,
'form': form,
'url_generator_enabled': url_generator_enabled,
'filesize': image.get_file_size(),
})
def url_generator(request, image_id):
image = get_object_or_404(get_video_model(), id=image_id)
form = URLGeneratorForm(initial={
'filter_method': 'original',
'width': image.width,
'height': image.height,
})
return render(request, "wagtailvideos/images/url_generator.html", {
'image': image,
'form': form,
})
def generate_url(request, image_id, filter_spec):
# Get the image
Image = get_video_model()
try:
Image.objects.get(id=image_id)
except Image.DoesNotExist:
return JsonResponse({
'error': "Cannot find image."
}, status=404)
# Check if this user has edit permission on this image
# Generate url
url = reverse('wagtailvideos_serve', args=(image_id, filter_spec))
# Get site root url
try:
site_root_url = Site.objects.get(is_default_site=True).root_url
except Site.DoesNotExist:
site_root_url = Site.objects.first().root_url
# Generate preview url
preview_url = reverse('wagtailvideos:preview', args=(image_id, filter_spec))
return JsonResponse({'url': site_root_url + url, 'preview_url': preview_url}, status=200)
def delete(request, image_id):
image = get_object_or_404(get_video_model(), id=image_id)
if request.POST:
image.delete()
messages.success(request, _("Image '{0}' deleted.").format(image.title))
return redirect('wagtailvideos:index')
return render(request, "wagtailvideos/images/confirm_delete.html", {
'image': image,
})
def add(request):
ImageModel = get_video_model()
ImageForm = get_video_form(ImageModel)
if request.POST:
image = ImageModel(uploaded_by_user=request.user)
form = ImageForm(request.POST, request.FILES, instance=image, user=request.user)
if form.is_valid():
# Set image file size
image.file_size = image.file.size
form.save()
# Reindex the image to make sure all tags are indexed
for backend in get_search_backends():
backend.add(image)
messages.success(request, _("Image '{0}' added.").format(image.title), buttons=[
messages.button(reverse('wagtailvideos:edit', args=(image.id,)), _('Edit'))
])
return redirect('wagtailvideos:index')
else:
messages.error(request, _("The image could not be created due to errors."))
else:
form = ImageForm(user=request.user)
return render(request, "wagtailvideos/images/add.html", {
'form': form,
})
def usage(request, image_id):
image = get_object_or_404(get_video_model(), id=image_id)
paginator, used_by = paginate(request, image.get_usage())
return render(request, "wagtailvideos/images/usage.html", {
'image': image,
'used_by': used_by
})
from __future__ import unicode_literals
from django.conf.urls import include, url
from django.contrib.staticfiles.templatetags.staticfiles import static
from django.core import urlresolvers
from django.utils.html import format_html, format_html_join
from django.utils.translation import ugettext_lazy as _
from wagtail.wagtailadmin.menu import MenuItem
from wagtail.wagtailcore import hooks
from . import urls
@hooks.register('register_admin_urls')
def register_admin_urls():
return [
url(r'^videos/', include(urls, namespace='wagtailvideos', app_name='wagtailvideos')),
]
@hooks.register('insert_editor_js')
def editor_js():
js_files = [
static('wagtailvideos/js/hallo-plugins/hallo-wagtailvideo.js'),
static('wagtailvideos/js/video-chooser.js'),
]
js_includes = format_html_join(
'\n', '<script src="{0}"></script>',
((filename, ) for filename in js_files)
)
return js_includes + format_html(
"""
<script>
window.chooserUrls.videoChooser = '{0}';
registerHalloPlugin('hallowagtailvideo');
</script>
""",
urlresolvers.reverse('wagtailvideos:chooser')
)
@hooks.register('register_admin_menu_item')
def register_images_menu_item():
return MenuItem(
_('Videos'), urlresolvers.reverse('wagtailvideos:index'),
name='videos', classnames='icon icon-video', order=300
)
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment