]> BookStack Code Mirror - bookstack/blob - resources/assets/js/vues/image-manager.js
Started work on drawing revisions
[bookstack] / resources / assets / js / vues / image-manager.js
1 const dropzone = require('./components/dropzone');
2
3 let page = 0;
4 let previousClickTime = 0;
5 let previousClickImage = 0;
6 let dataLoaded = false;
7 let callback = false;
8 let baseUrl = '';
9
10 let preSearchImages = [];
11 let preSearchHasMore = false;
12
13 const data = {
14     images: [],
15
16     imageType: false,
17     uploadedTo: false,
18
19     selectedImage: false,
20     dependantPages: false,
21     showing: false,
22     view: 'all',
23     hasMore: false,
24     searching: false,
25     searchTerm: '',
26
27     imageUpdateSuccess: false,
28     imageDeleteSuccess: false,
29     deleteConfirm: false,
30 };
31
32 const methods = {
33
34     show(providedCallback, imageType = null) {
35         callback = providedCallback;
36         this.showing = true;
37         this.$el.children[0].components.overlay.show();
38
39         // Get initial images if they have not yet been loaded in.
40         if (dataLoaded && imageType === this.imageType) return;
41         if (imageType) {
42             this.imageType = imageType;
43             this.resetState();
44         }
45         this.fetchData();
46         dataLoaded = true;
47     },
48
49     hide() {
50         this.showing = false;
51         this.selectedImage = false;
52         this.$refs.dropzone.onClose();
53         this.$el.children[0].components.overlay.hide();
54     },
55
56     fetchData() {
57         let url = baseUrl + page;
58         let query = {};
59         if (this.uploadedTo !== false) query.page_id = this.uploadedTo;
60         if (this.searching) query.term = this.searchTerm;
61
62         this.$http.get(url, {params: query}).then(response => {
63             this.images = this.images.concat(response.data.images);
64             this.hasMore = response.data.hasMore;
65             page++;
66         });
67     },
68
69     setView(viewName) {
70         this.view = viewName;
71         this.resetState();
72         this.fetchData();
73     },
74
75     resetState() {
76         this.cancelSearch();
77         this.images = [];
78         this.hasMore = false;
79         this.deleteConfirm = false;
80         page = 0;
81         baseUrl = window.baseUrl(`/images/${this.imageType}/${this.view}/`);
82     },
83
84     searchImages() {
85         if (this.searchTerm === '') return this.cancelSearch();
86
87         // Cache current settings for later
88         if (!this.searching) {
89             preSearchImages = this.images;
90             preSearchHasMore = this.hasMore;
91         }
92
93         this.searching = true;
94         this.images = [];
95         this.hasMore = false;
96         page = 0;
97         baseUrl = window.baseUrl(`/images/${this.imageType}/search/`);
98         this.fetchData();
99     },
100
101     cancelSearch() {
102         this.searching = false;
103         this.searchTerm = '';
104         this.images = preSearchImages;
105         this.hasMore = preSearchHasMore;
106     },
107
108     imageSelect(image) {
109         let dblClickTime = 300;
110         let currentTime = Date.now();
111         let timeDiff = currentTime - previousClickTime;
112         let isDblClick = timeDiff < dblClickTime && image.id === previousClickImage;
113
114         if (isDblClick) {
115             this.callbackAndHide(image);
116         } else {
117             this.selectedImage = image;
118             this.deleteConfirm = false;
119             this.dependantPages = false;
120         }
121
122         previousClickTime = currentTime;
123         previousClickImage = image.id;
124     },
125
126     callbackAndHide(imageResult) {
127         if (callback) callback(imageResult);
128         this.hide();
129     },
130
131     saveImageDetails() {
132         let url = window.baseUrl(`/images/update/${this.selectedImage.id}`);
133         this.$http.put(url, this.selectedImage).then(response => {
134             this.$events.emit('success', trans('components.image_update_success'));
135         }).catch(error => {
136             if (error.response.status === 422) {
137                 let errors = error.response.data;
138                 let message = '';
139                 Object.keys(errors).forEach((key) => {
140                     message += errors[key].join('\n');
141                 });
142                 this.$events.emit('error', message);
143             }
144         });
145     },
146
147     deleteImage() {
148
149         if (!this.deleteConfirm) {
150             let url = window.baseUrl(`/images/usage/${this.selectedImage.id}`);
151             this.$http.get(url).then(resp => {
152                 this.dependantPages = resp.data;
153             }).catch(console.error).then(() => {
154                 this.deleteConfirm = true;
155             });
156             return;
157         }
158
159         this.$http.delete(`/images/${this.selectedImage.id}`).then(resp => {
160             this.images.splice(this.images.indexOf(this.selectedImage), 1);
161             this.selectedImage = false;
162             this.$events.emit('success', trans('components.image_delete_success'));
163             this.deleteConfirm = false;
164         });
165     },
166
167     getDate(stringDate) {
168         return new Date(stringDate);
169     },
170
171     uploadSuccess(event) {
172         this.images.unshift(event.data);
173         this.$events.emit('success', trans('components.image_upload_success'));
174     },
175 };
176
177 const computed = {
178     uploadUrl() {
179         return window.baseUrl(`/images/${this.imageType}/upload`);
180     }
181 };
182
183 function mounted() {
184     window.ImageManager = this;
185     this.imageType = this.$el.getAttribute('image-type');
186     this.uploadedTo = this.$el.getAttribute('uploaded-to');
187     baseUrl = window.baseUrl('/images/' + this.imageType + '/all/')
188 }
189
190 module.exports = {
191     mounted,
192     methods,
193     data,
194     computed,
195     components: {dropzone},
196 };