##// END OF EJS Templates
Fixed popup image preview
neko259 -
r1596:b556dd6b default
parent child Browse files
Show More
@@ -1,78 +1,78 b''
1 1 import boards
2 2 from boards.models import STATUS_ARCHIVE
3 3 from django.core.files.images import get_image_dimensions
4 4 from django.db import models
5 5
6 6 from boards import utils
7 7 from boards.models.attachment.viewers import get_viewers, AbstractViewer, \
8 8 FILE_TYPES_IMAGE
9 9 from boards.utils import get_upload_filename, get_extension, cached_result
10 10
11 11
12 12 class AttachmentManager(models.Manager):
13 13 def create_with_hash(self, file):
14 14 file_hash = utils.get_file_hash(file)
15 15 existing = self.filter(hash=file_hash)
16 16 if len(existing) > 0:
17 17 attachment = existing[0]
18 18 else:
19 19 # FIXME Use full mimetype here, need to modify viewers too
20 20 file_type = get_extension(file.name)
21 21 attachment = self.create(file=file, mimetype=file_type,
22 22 hash=file_hash)
23 23
24 24 return attachment
25 25
26 26 def get_random_images(self, count, tags=None):
27 27 images = self.filter(mimetype__in=FILE_TYPES_IMAGE).exclude(
28 28 attachment_posts__thread__status=STATUS_ARCHIVE)
29 29 if tags is not None:
30 30 images = images.filter(attachment_posts__threads__tags__in=tags)
31 31 return images.order_by('?')[:count]
32 32
33 33
34 34 class Attachment(models.Model):
35 35 objects = AttachmentManager()
36 36
37 37 file = models.FileField(upload_to=get_upload_filename)
38 38 mimetype = models.CharField(max_length=50)
39 39 hash = models.CharField(max_length=36)
40 40 alias = models.TextField(unique=True, null=True, blank=True)
41 41
42 42 def get_view(self):
43 43 file_viewer = None
44 44 for viewer in get_viewers():
45 45 if viewer.supports(self.mimetype):
46 46 file_viewer = viewer
47 47 break
48 48 if file_viewer is None:
49 49 file_viewer = AbstractViewer
50 50
51 return file_viewer(self.file, self.mimetype).get_view()
51 return file_viewer(self.file, self.mimetype, self.hash).get_view()
52 52
53 53 def __str__(self):
54 54 return self.file.url
55 55
56 56 def get_random_associated_post(self):
57 57 posts = boards.models.Post.objects.filter(attachments__in=[self])
58 58 return posts.order_by('?').first()
59 59
60 60 @cached_result()
61 61 def get_size(self):
62 62 if self.mimetype in FILE_TYPES_IMAGE:
63 63 return get_image_dimensions(self.file)
64 64 else:
65 65 return 200, 150
66 66
67 67 def get_thumb_url(self):
68 68 split = self.file.url.rsplit('.', 1)
69 69 w, h = 200, 150
70 70 return '%s.%sx%s.%s' % (split[0], w, h, split[1])
71 71
72 72 @cached_result()
73 73 def get_preview_size(self):
74 74 if self.mimetype in FILE_TYPES_IMAGE:
75 75 preview_path = self.file.path.replace('.', '.200x150.')
76 76 return get_image_dimensions(preview_path)
77 77 else:
78 78 return 200, 150
@@ -1,128 +1,131 b''
1 1 from django.core.files.images import get_image_dimensions
2 2 from django.template.defaultfilters import filesizeformat
3 3 from django.contrib.staticfiles.templatetags.staticfiles import static
4 4
5 5 FILE_STUB_IMAGE = 'images/file.png'
6 6
7 7 FILE_TYPES_VIDEO = (
8 8 'webm',
9 9 'mp4',
10 10 'mpeg',
11 11 'ogv',
12 12 )
13 13 FILE_TYPE_SVG = 'svg'
14 14 FILE_TYPES_AUDIO = (
15 15 'ogg',
16 16 'mp3',
17 17 'opus',
18 18 )
19 19 FILE_TYPES_IMAGE = (
20 20 'jpeg',
21 21 'jpg',
22 22 'png',
23 23 'bmp',
24 24 'gif',
25 25 )
26 26
27 27 PLAIN_FILE_FORMATS = {
28 28 'pdf': 'pdf',
29 29 'djvu': 'djvu',
30 30 'txt': 'txt',
31 31 }
32 32
33 33 CSS_CLASS_IMAGE = 'image'
34 34 CSS_CLASS_THUMB = 'thumb'
35 35
36 36
37 37 def get_viewers():
38 38 return AbstractViewer.__subclasses__()
39 39
40 40
41 41 class AbstractViewer:
42 def __init__(self, file, file_type):
42 def __init__(self, file, file_type, hash):
43 43 self.file = file
44 44 self.file_type = file_type
45 self.hash = hash
45 46
46 47 @staticmethod
47 48 def supports(file_type):
48 49 return True
49 50
50 51 def get_view(self):
51 52 return '<div class="image">'\
52 53 '{}'\
53 54 '<div class="image-metadata"><a href="{}" download >{}, {}</a></div>'\
54 55 '</div>'.format(self.get_format_view(), self.file.url,
55 56 self.file_type, filesizeformat(self.file.size))
56 57
57 58 def get_format_view(self):
58 59 if self.file_type in PLAIN_FILE_FORMATS:
59 60 image = 'images/fileformats/{}.png'.format(
60 61 PLAIN_FILE_FORMATS[self.file_type])
61 62 else:
62 63 image = FILE_STUB_IMAGE
63 64
64 65 return '<a href="{}">'\
65 66 '<img src="{}" width="200" height="150"/>'\
66 67 '</a>'.format(self.file.url, static(image))
67 68
68 69
69 70 class VideoViewer(AbstractViewer):
70 71 @staticmethod
71 72 def supports(file_type):
72 73 return file_type in FILE_TYPES_VIDEO
73 74
74 75 def get_format_view(self):
75 76 return '<video width="200" height="150" controls src="{}"></video>'\
76 77 .format(self.file.url)
77 78
78 79
79 80 class AudioViewer(AbstractViewer):
80 81 @staticmethod
81 82 def supports(file_type):
82 83 return file_type in FILE_TYPES_AUDIO
83 84
84 85 def get_format_view(self):
85 86 return '<audio controls src="{}"></audio>'.format(self.file.url)
86 87
87 88
88 89 class SvgViewer(AbstractViewer):
89 90 @staticmethod
90 91 def supports(file_type):
91 92 return file_type == FILE_TYPE_SVG
92 93
93 94 def get_format_view(self):
94 95 return '<a class="thumb" href="{}">'\
95 96 '<img class="post-image-preview" width="200" height="150" src="{}" />'\
96 97 '</a>'.format(self.file.url, self.file.url)
97 98
98 99
99 100 class ImageViewer(AbstractViewer):
100 101 @staticmethod
101 102 def supports(file_type):
102 103 return file_type in FILE_TYPES_IMAGE
103 104
104 105 def get_format_view(self):
105 106 metadata = '{}, {}'.format(self.file.name.split('.')[-1],
106 107 filesizeformat(self.file.size))
107 108 width, height = get_image_dimensions(self.file.file)
108 109 preview_path = self.file.path.replace('.', '.200x150.')
109 110 pre_width, pre_height = get_image_dimensions(preview_path)
110 111
111 112 split = self.file.url.rsplit('.', 1)
112 113 w, h = 200, 150
113 114 thumb_url = '%s.%sx%s.%s' % (split[0], w, h, split[1])
114 115
115 116 return '<a class="{}" href="{full}">' \
116 117 '<img class="post-image-preview"' \
117 118 ' src="{}"' \
119 ' alt="{}"' \
118 120 ' width="{}"' \
119 121 ' height="{}"' \
120 122 ' data-width="{}"' \
121 123 ' data-height="{}" />' \
122 124 '</a>' \
123 125 .format(CSS_CLASS_THUMB,
124 126 thumb_url,
127 self.hash,
125 128 str(pre_width),
126 129 str(pre_height), str(width), str(height),
127 130 full=self.file.url, image_meta=metadata)
128 131
General Comments 0
You need to be logged in to leave comments. Login now