Browse Source

Add federated photo filters

Daniel Supernault 4 years ago
parent
commit
0a5a0e8616

+ 3 - 0
app/Http/Controllers/MediaController.php

@@ -41,6 +41,9 @@ class MediaController extends Controller
 			->whereNull('status_id')
 			->findOrFail($id);
 
+		$media->version = 2;
+		$media->save();
+
 		$fragments = explode('/', $media->media_path);
 		$name = last($fragments);
 		array_pop($fragments);

+ 1 - 1
app/Transformer/Api/MediaTransformer.php

@@ -22,7 +22,7 @@ class MediaTransformer extends Fractal\TransformerAbstract
             'is_nsfw'       => $media->is_nsfw,
             'orientation'   => $media->orientation,
             'filter_name'   => $media->filter_name,
-            'filter_class'  => $media->filter_class,
+            'filter_class'  => $media->version == 1 ? $media->filter_class : null,
             'mime'          => $media->mime,
         ];
     }

+ 43 - 0
resources/assets/js/app.js

@@ -139,6 +139,49 @@ window.App.util = {
 			['Willow','filter-willow'], 
 			['X-Pro II','filter-xpro-ii']
 	],
+	filterCss: {
+		'filter-1977': 'sepia(.5) hue-rotate(-30deg) saturate(1.4)',
+		'filter-aden': 'sepia(.2) brightness(1.15) saturate(1.4)',
+		'filter-amaro': 'sepia(.35) contrast(1.1) brightness(1.2) saturate(1.3)',
+		'filter-ashby': 'sepia(.5) contrast(1.2) saturate(1.8)',
+		'filter-brannan': 'sepia(.4) contrast(1.25) brightness(1.1) saturate(.9) hue-rotate(-2deg)',
+		'filter-brooklyn': 'sepia(.25) contrast(1.25) brightness(1.25) hue-rotate(5deg)',
+		'filter-charmes': 'sepia(.25) contrast(1.25) brightness(1.25) saturate(1.35) hue-rotate(-5deg)',
+		'filter-clarendon': 'sepia(.15) contrast(1.25) brightness(1.25) hue-rotate(5deg)',
+		'filter-crema': 'sepia(.5) contrast(1.25) brightness(1.15) saturate(.9) hue-rotate(-2deg)',
+		'filter-dogpatch': 'sepia(.35) saturate(1.1) contrast(1.5)',
+		'filter-earlybird': 'sepia(.25) contrast(1.25) brightness(1.15) saturate(.9) hue-rotate(-5deg)',
+		'filter-gingham': 'contrast(1.1) brightness(1.1)',
+		'filter-ginza': 'sepia(.25) contrast(1.15) brightness(1.2) saturate(1.35) hue-rotate(-5deg)',
+		'filter-hefe': 'sepia(.4) contrast(1.5) brightness(1.2) saturate(1.4) hue-rotate(-10deg)',
+		'filter-helena': 'sepia(.5) contrast(1.05) brightness(1.05) saturate(1.35)',
+		'filter-hudson': 'sepia(.25) contrast(1.2) brightness(1.2) saturate(1.05) hue-rotate(-15deg)',
+		'filter-inkwell': 'brightness(1.25) contrast(.85) grayscale(1)',
+		'filter-kelvin': 'sepia(.15) contrast(1.5) brightness(1.1) hue-rotate(-10deg)',
+		'filter-juno': 'sepia(.35) contrast(1.15) brightness(1.15) saturate(1.8)',
+		'filter-lark': 'sepia(.25) contrast(1.2) brightness(1.3) saturate(1.25)',
+		'filter-lofi': 'saturate(1.1) contrast(1.5)',
+		'filter-ludwig': 'sepia(.25) contrast(1.05) brightness(1.05) saturate(2)',
+		'filter-maven': 'sepia(.35) contrast(1.05) brightness(1.05) saturate(1.75)',
+		'filter-mayfair': 'contrast(1.1) brightness(1.15) saturate(1.1)',
+		'filter-moon': 'brightness(1.4) contrast(.95) saturate(0) sepia(.35)',
+		'filter-nashville': 'sepia(.25) contrast(1.5) brightness(.9) hue-rotate(-15deg)',
+		'filter-perpetua': 'contrast(1.1) brightness(1.25) saturate(1.1)',
+		'filter-poprocket': 'sepia(.15) brightness(1.2)',
+		'filter-reyes': 'sepia(.75) contrast(.75) brightness(1.25) saturate(1.4)',
+		'filter-rise': 'sepia(.25) contrast(1.25) brightness(1.2) saturate(.9)',
+		'filter-sierra': 'sepia(.25) contrast(1.5) brightness(.9) hue-rotate(-15deg)',
+		'filter-skyline': 'sepia(.15) contrast(1.25) brightness(1.25) saturate(1.2)',
+		'filter-slumber': 'sepia(.35) contrast(1.25) saturate(1.25)',
+		'filter-stinson': 'sepia(.35) contrast(1.25) brightness(1.1) saturate(1.25)',
+		'filter-sutro': 'sepia(.4) contrast(1.2) brightness(.9) saturate(1.4) hue-rotate(-10deg)',
+		'filter-toaster': 'sepia(.25) contrast(1.5) brightness(.95) hue-rotate(-15deg)',
+		'filter-valencia': 'sepia(.25) contrast(1.1) brightness(1.1)',
+		'filter-vesper': 'sepia(.35) contrast(1.15) brightness(1.2) saturate(1.3)',
+		'filter-walden': 'sepia(.35) contrast(.8) brightness(1.25) saturate(1.4)',
+		'filter-willow': 'brightness(1.2) contrast(.85) saturate(.05) sepia(.2)',
+		'filter-xpro-ii': 'sepia(.45) contrast(1.25) brightness(1.75) saturate(1.3) hue-rotate(-5deg)'
+	},
 	emoji: ['๐Ÿ˜‚','๐Ÿ’ฏ','โค๏ธ','๐Ÿ™Œ','๐Ÿ‘','๐Ÿ‘Œ','๐Ÿ˜','๐Ÿ˜ฏ','๐Ÿ˜ข','๐Ÿ˜…','๐Ÿ˜','๐Ÿ™‚','๐Ÿ˜Ž','๐Ÿ˜€','๐Ÿคฃ','๐Ÿ˜ƒ','๐Ÿ˜„','๐Ÿ˜†','๐Ÿ˜‰','๐Ÿ˜Š','๐Ÿ˜‹','๐Ÿ˜˜','๐Ÿ˜—','๐Ÿ˜™','๐Ÿ˜š','๐Ÿค—','๐Ÿคฉ','๐Ÿค”','๐Ÿคจ','๐Ÿ˜','๐Ÿ˜‘','๐Ÿ˜ถ','๐Ÿ™„','๐Ÿ˜','๐Ÿ˜ฃ','๐Ÿ˜ฅ','๐Ÿ˜ฎ','๐Ÿค','๐Ÿ˜ช','๐Ÿ˜ซ','๐Ÿ˜ด','๐Ÿ˜Œ','๐Ÿ˜›','๐Ÿ˜œ','๐Ÿ˜','๐Ÿคค','๐Ÿ˜’','๐Ÿ˜“','๐Ÿ˜”','๐Ÿ˜•','๐Ÿ™ƒ','๐Ÿค‘','๐Ÿ˜ฒ','๐Ÿ™','๐Ÿ˜–','๐Ÿ˜ž','๐Ÿ˜Ÿ','๐Ÿ˜ค','๐Ÿ˜ญ','๐Ÿ˜ฆ','๐Ÿ˜ง','๐Ÿ˜จ','๐Ÿ˜ฉ','๐Ÿคฏ','๐Ÿ˜ฌ','๐Ÿ˜ฐ','๐Ÿ˜ฑ','๐Ÿ˜ณ','๐Ÿคช','๐Ÿ˜ต','๐Ÿ˜ก','๐Ÿ˜ ','๐Ÿคฌ','๐Ÿ˜ท','๐Ÿค’','๐Ÿค•','๐Ÿคข','๐Ÿคฎ','๐Ÿคง','๐Ÿ˜‡','๐Ÿค ','๐Ÿคก','๐Ÿคฅ','๐Ÿคซ','๐Ÿคญ','๐Ÿง','๐Ÿค“','๐Ÿ˜ˆ','๐Ÿ‘ฟ','๐Ÿ‘น','๐Ÿ‘บ','๐Ÿ’€','๐Ÿ‘ป','๐Ÿ‘ฝ','๐Ÿค–','๐Ÿ’ฉ','๐Ÿ˜บ','๐Ÿ˜ธ','๐Ÿ˜น','๐Ÿ˜ป','๐Ÿ˜ผ','๐Ÿ˜ฝ','๐Ÿ™€','๐Ÿ˜ฟ','๐Ÿ˜พ','๐Ÿคฒ','๐Ÿ‘','๐Ÿค','๐Ÿ‘','๐Ÿ‘Ž','๐Ÿ‘Š','โœŠ','๐Ÿค›','๐Ÿคœ','๐Ÿคž','โœŒ๏ธ','๐ŸคŸ','๐Ÿค˜','๐Ÿ‘ˆ','๐Ÿ‘‰','๐Ÿ‘†','๐Ÿ‘‡','โ˜๏ธ','โœ‹','๐Ÿคš','๐Ÿ–','๐Ÿ––','๐Ÿ‘‹','๐Ÿค™','๐Ÿ’ช','๐Ÿ–•','โœ๏ธ','๐Ÿ™','๐Ÿ’','๐Ÿ’„','๐Ÿ’‹','๐Ÿ‘„','๐Ÿ‘…','๐Ÿ‘‚','๐Ÿ‘ƒ','๐Ÿ‘ฃ','๐Ÿ‘','๐Ÿ‘€','๐Ÿง ','๐Ÿ—ฃ','๐Ÿ‘ค','๐Ÿ‘ฅ'
 	],
 	embed: {

+ 33 - 0
resources/assets/js/components/ComposeModal.vue

@@ -1,6 +1,8 @@
 <template>
 <div>
 	<input type="file" id="pf-dz" name="media" class="w-100 h-100 d-none file-input" v-bind:accept="config.uploader.media_types">
+	<canvas class="d-none" id="pr_canvas"></canvas>
+	<img class="d-none" id="pr_img">
 	<div class="timeline">
 		<div v-if="uploading">
 			<div class="card status-card card-md-rounded-0 w-100 h-100 bg-light py-3" style="border-bottom: 1px solid #f1f1f1">
@@ -983,9 +985,40 @@ export default {
 				this.cameraRollMedia = res.data;
 			});
 		},
+
 		applyFilterToMedia() {
 			// this is where the magic happens
 
+			let medias = this.media;
+			let media = null;
+			const canvas = document.getElementById('pr_canvas');
+			const ctx = canvas.getContext('2d');
+			let image = document.getElementById('pr_img');
+			let blob = null;
+			let data = null;
+
+			for (var i = medias.length - 1; i >= 0; i--) {
+				media = medias[i];
+				if(media.filter_class) {
+					image.src = media.url;
+					image.addEventListener('load', e => {
+						canvas.width = image.width;
+						canvas.height = image.height;
+						ctx.filter = App.util.filterCss[media.filter_class];
+						ctx.drawImage(image, 0, 0, image.width, image.height);
+						ctx.save();
+						canvas.toBlob(function(blob) {
+							data = new FormData();
+							data.append('file', blob);
+							axios.post('/api/local/compose/media/update/'+media.id, data).then(res => {
+							}).catch(err => {
+							});
+						}, media.mime, 0.9);
+					});
+					ctx.clearRect(0, 0, image.width, image.height);
+				}
+			}
+
 		},
 
 		tagSearch(input) {