Bläddra i källkod

Merge pull request #2375 from pixelfed/staging

Staging
daniel 4 år sedan
förälder
incheckning
90000f1350

+ 1 - 0
CHANGELOG.md

@@ -84,6 +84,7 @@
 - Updated Profile.vue, add atom feed link to context menu. Fixes ([#2313](https://github.com/pixelfed/pixelfed/issues/2313)). ([89f29072](https://github.com/pixelfed/pixelfed/commit/89f29072))
 - Updated Hashtag.vue, add nsfw toggle. Fixes ([#2225](https://github.com/pixelfed/pixelfed/issues/2225)). ([e5aa506c](https://github.com/pixelfed/pixelfed/commit/e5aa506c))
 - Updated Timeline.vue, move compose button. ([9cad8f77](https://github.com/pixelfed/pixelfed/commit/9cad8f77))
+- Updated status embed, allow photo albums. Fixes ([#2374](https://github.com/pixelfed/pixelfed/issues/2374)). ([d11fac0d](https://github.com/pixelfed/pixelfed/commit/d11fac0d))
 
 ## [v0.10.9 (2020-04-17)](https://github.com/pixelfed/pixelfed/compare/v0.10.8...v0.10.9)
 ### Added

+ 4 - 0
app/Http/Controllers/Auth/RegisterController.php

@@ -68,6 +68,10 @@ class RegisterController extends Controller
                 $underscore = substr_count($value, '_');
                 $period = substr_count($value, '.');
 
+                if(ends_with($value, ['.php', '.js', '.css'])) {
+                    return $fail('Username is invalid.');
+                }
+
                 if(($dash + $underscore + $period) > 1) {
                     return $fail('Username is invalid. Can only contain one dash (-), period (.) or underscore (_).');
                 }

+ 3 - 2
app/Http/Controllers/StatusController.php

@@ -68,7 +68,8 @@ class StatusController extends Controller
 
     public function shortcodeRedirect(Request $request, $id)
     {
-        if(strlen($id) < 5 || !Auth::check()) {
+        abort_if(strlen($id) < 5, 404);
+        if(!Auth::check()) {
             return redirect('/login?next='.urlencode('/' . $request->path()));
         }
         $id = HashidService::decode($id);
@@ -99,7 +100,7 @@ class StatusController extends Controller
             ->whereNull('uri')
             ->whereScope('public')
             ->whereIsNsfw(false)
-            ->whereIn('type', ['photo', 'video'])
+            ->whereIn('type', ['photo', 'video','photo:album'])
             ->find($id);
         if(!$status) {
             $content = view('status.embed-removed');

+ 5 - 0
app/Util/Lexer/RestrictedNames.php

@@ -85,6 +85,7 @@ class RestrictedNames
 
 		// Static Assets
 		'assets',
+		'public',
 		'storage',
 
 		// Laravel Horizon
@@ -141,6 +142,8 @@ class RestrictedNames
 		'drives',
 		'driver',
 		'e',
+		'embed',
+		'embed.js',
 		'email',
 		'emails',
 		'error',
@@ -182,6 +185,7 @@ class RestrictedNames
 		'invites',
 		'import',
 		'imports',
+		'index.php',
 		'j',
 		'js',
 		'k',
@@ -280,6 +284,7 @@ class RestrictedNames
 		'whatsnew',
 		'whatnew',
 		'whats-news',
+		'web',
 		'ws',
 		'wss',
 		'www',

+ 124 - 87
package-lock.json

@@ -831,9 +831,9 @@
             }
         },
         "@trevoreyre/autocomplete-vue": {
-            "version": "2.1.1",
-            "resolved": "https://registry.npmjs.org/@trevoreyre/autocomplete-vue/-/autocomplete-vue-2.1.1.tgz",
-            "integrity": "sha512-zeVzjRliM5Yv0oaBNPE3OX4U5K59jwo/OC62Qi6SE1Fd6mwO6q6MXVogmujrOrdalIqDHQo8pUvhTFL4Xr/Rfw=="
+            "version": "2.2.0",
+            "resolved": "https://registry.npmjs.org/@trevoreyre/autocomplete-vue/-/autocomplete-vue-2.2.0.tgz",
+            "integrity": "sha512-A5j986nM6htTbCpEW9BbwlqCobIMD4+uicAYGCSI8DM1ojK8meCyVI23jK+gAxi+vjhraCBneKI+vbwB8sL0ig=="
         },
         "@types/events": {
             "version": "3.0.0",
@@ -1160,6 +1160,11 @@
             "resolved": "https://registry.npmjs.org/amdefine/-/amdefine-1.0.1.tgz",
             "integrity": "sha1-SlKCrBZHKek2Gbz9OtFR+BfOkfU="
         },
+        "animate.css": {
+            "version": "4.1.0",
+            "resolved": "https://registry.npmjs.org/animate.css/-/animate.css-4.1.0.tgz",
+            "integrity": "sha512-0aVcfWDeU9ykV6vjn1P67ZSs01jxoUQZCGaYbkk0SIIelIG8kUdLrIkua1+VabHfTtsSivDRMMn0ILPvZum2gw=="
+        },
         "ansi-colors": {
             "version": "3.2.4",
             "resolved": "https://registry.npmjs.org/ansi-colors/-/ansi-colors-3.2.4.tgz",
@@ -1312,7 +1317,7 @@
                 },
                 "util": {
                     "version": "0.10.3",
-                    "resolved": "https://registry.npmjs.org/util/-/util-0.10.3.tgz",
+                    "resolved": "http://registry.npmjs.org/util/-/util-0.10.3.tgz",
                     "integrity": "sha1-evsa/lCAUkZInj23/g7TeTNqwPk=",
                     "requires": {
                         "inherits": "2.0.1"
@@ -1436,7 +1441,7 @@
                 },
                 "chalk": {
                     "version": "1.1.3",
-                    "resolved": "https://registry.npmjs.org/chalk/-/chalk-1.1.3.tgz",
+                    "resolved": "http://registry.npmjs.org/chalk/-/chalk-1.1.3.tgz",
                     "integrity": "sha1-qBFcVeSnAv5NFQq9OHKCKn4J/Jg=",
                     "requires": {
                         "ansi-styles": "^2.2.1",
@@ -1453,7 +1458,7 @@
                 },
                 "supports-color": {
                     "version": "2.0.0",
-                    "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-2.0.0.tgz",
+                    "resolved": "http://registry.npmjs.org/supports-color/-/supports-color-2.0.0.tgz",
                     "integrity": "sha1-U10EXOa2Nj+kARcIRimZXp3zJMc="
                 }
             }
@@ -1700,17 +1705,17 @@
             "integrity": "sha1-aN/1++YMUes3cl6p4+0xDcwed24="
         },
         "bootstrap": {
-            "version": "4.5.0",
-            "resolved": "https://registry.npmjs.org/bootstrap/-/bootstrap-4.5.0.tgz",
-            "integrity": "sha512-Z93QoXvodoVslA+PWNdk23Hze4RBYIkpb5h8I2HY2Tu2h7A0LpAgLcyrhrSUyo2/Oxm2l1fRZPs1e5hnxnliXA=="
+            "version": "4.5.2",
+            "resolved": "https://registry.npmjs.org/bootstrap/-/bootstrap-4.5.2.tgz",
+            "integrity": "sha512-vlGn0bcySYl/iV+BGA544JkkZP5LB3jsmkeKLFQakCOwCM3AOk7VkldBz4jrzSe+Z0Ezn99NVXa1o45cQY4R6A=="
         },
         "bootstrap-vue": {
-            "version": "2.14.0",
-            "resolved": "https://registry.npmjs.org/bootstrap-vue/-/bootstrap-vue-2.14.0.tgz",
-            "integrity": "sha512-sqbS7iHYCZEj/dDx4Yaze99HcX6bZjO4bSWZ0xSgJwtWQlbfB2VDJ9Qjzjp9XI8TT32wYNGAMpnXpYjQvv5qyQ==",
+            "version": "2.16.0",
+            "resolved": "https://registry.npmjs.org/bootstrap-vue/-/bootstrap-vue-2.16.0.tgz",
+            "integrity": "sha512-gLETwPmeRHCe5WHmhGxzb5PtTEuKqQPGl0TFvZ2Odbkg/7UuIHdqIexrJRerpnomP4ZzDQ+qYGL91Ls9lcQsJQ==",
             "requires": {
                 "@nuxt/opencollective": "^0.3.0",
-                "bootstrap": ">=4.4.1 <5.0.0",
+                "bootstrap": ">=4.5.0 <5.0.0",
                 "popper.js": "^1.16.1",
                 "portal-vue": "^2.1.7",
                 "vue-functional-data-merge": "^3.1.0"
@@ -1764,7 +1769,7 @@
         },
         "browserify-aes": {
             "version": "1.2.0",
-            "resolved": "https://registry.npmjs.org/browserify-aes/-/browserify-aes-1.2.0.tgz",
+            "resolved": "http://registry.npmjs.org/browserify-aes/-/browserify-aes-1.2.0.tgz",
             "integrity": "sha512-+7CHXqGuspUn/Sl5aO7Ea0xWGAtETPXNSAjHo48JfLdPWcMng33Xe4znFvQweqc/uzk5zSOI3H52CYnjCfb5hA==",
             "requires": {
                 "buffer-xor": "^1.0.3",
@@ -1798,7 +1803,7 @@
         },
         "browserify-rsa": {
             "version": "4.0.1",
-            "resolved": "https://registry.npmjs.org/browserify-rsa/-/browserify-rsa-4.0.1.tgz",
+            "resolved": "http://registry.npmjs.org/browserify-rsa/-/browserify-rsa-4.0.1.tgz",
             "integrity": "sha1-IeCr+vbyApzy+vsTNWenAdQTVSQ=",
             "requires": {
                 "bn.js": "^4.1.0",
@@ -2349,7 +2354,7 @@
         },
         "concat-stream": {
             "version": "1.6.2",
-            "resolved": "https://registry.npmjs.org/concat-stream/-/concat-stream-1.6.2.tgz",
+            "resolved": "http://registry.npmjs.org/concat-stream/-/concat-stream-1.6.2.tgz",
             "integrity": "sha512-27HBghJxjiZtIk3Ycvn/4kbJk/1uZuJFfuPEns6LaEvpvG1f0hTea8lilrouyo9mVc2GWdcEZ8OLoGmSADlrCw==",
             "requires": {
                 "buffer-from": "^1.0.0",
@@ -2372,9 +2377,9 @@
             "integrity": "sha512-e54B99q/OUoH64zYYRf3HBP5z24G38h5D3qXu23JGRoigpX5Ss4r9ZnDk3g0Z8uQC2x2lPaJ+UlWBc1ZWBWdLg=="
         },
         "consola": {
-            "version": "2.12.1",
-            "resolved": "https://registry.npmjs.org/consola/-/consola-2.12.1.tgz",
-            "integrity": "sha512-aEkkju9ZcEa9y2MhzNhfmTUws/CEZZ0LKu0FxftSU3HygPfVMMIMSYyYct+xBN6XNRhsaDZjw2HAv3m2ammXSA=="
+            "version": "2.15.0",
+            "resolved": "https://registry.npmjs.org/consola/-/consola-2.15.0.tgz",
+            "integrity": "sha512-vlcSGgdYS26mPf7qNi+dCisbhiyDnrN1zaRbw3CSuc2wGOMEGGPsp46PdRG5gqXwgtJfjxDkxRNAgRPr1B77vQ=="
         },
         "console-browserify": {
             "version": "1.2.0",
@@ -2499,7 +2504,7 @@
         },
         "create-hash": {
             "version": "1.2.0",
-            "resolved": "https://registry.npmjs.org/create-hash/-/create-hash-1.2.0.tgz",
+            "resolved": "http://registry.npmjs.org/create-hash/-/create-hash-1.2.0.tgz",
             "integrity": "sha512-z00bCGNHDG8mHAkP7CtT1qVu+bFQUPjYq/4Iv3C3kWjTFV10zIjfSoeqXo9Asws8gwSHDGj/hl2u4OGIjapeCg==",
             "requires": {
                 "cipher-base": "^1.0.1",
@@ -2511,7 +2516,7 @@
         },
         "create-hmac": {
             "version": "1.1.7",
-            "resolved": "https://registry.npmjs.org/create-hmac/-/create-hmac-1.1.7.tgz",
+            "resolved": "http://registry.npmjs.org/create-hmac/-/create-hmac-1.1.7.tgz",
             "integrity": "sha512-MJG9liiZ+ogc4TzUwuvbER1JRdgvUFSB5+VR/g5h82fGaIRWMWddtKBHi7/sVhfjQZ6SehlyhvQYrcYkaUIpLg==",
             "requires": {
                 "cipher-base": "^1.0.3",
@@ -2661,12 +2666,12 @@
             "dependencies": {
                 "jsesc": {
                     "version": "0.5.0",
-                    "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-0.5.0.tgz",
+                    "resolved": "http://registry.npmjs.org/jsesc/-/jsesc-0.5.0.tgz",
                     "integrity": "sha1-597mbjXW/Bb3EP6R1c9p9w8IkR0="
                 },
                 "regexpu-core": {
                     "version": "1.0.0",
-                    "resolved": "https://registry.npmjs.org/regexpu-core/-/regexpu-core-1.0.0.tgz",
+                    "resolved": "http://registry.npmjs.org/regexpu-core/-/regexpu-core-1.0.0.tgz",
                     "integrity": "sha1-hqdj9Y7k18L2sQLkdkBQ3n7ZDGs=",
                     "requires": {
                         "regenerate": "^1.2.1",
@@ -2676,12 +2681,12 @@
                 },
                 "regjsgen": {
                     "version": "0.2.0",
-                    "resolved": "https://registry.npmjs.org/regjsgen/-/regjsgen-0.2.0.tgz",
+                    "resolved": "http://registry.npmjs.org/regjsgen/-/regjsgen-0.2.0.tgz",
                     "integrity": "sha1-bAFq3qxVT3WCP+N6wFuS1aTtsfc="
                 },
                 "regjsparser": {
                     "version": "0.1.5",
-                    "resolved": "https://registry.npmjs.org/regjsparser/-/regjsparser-0.1.5.tgz",
+                    "resolved": "http://registry.npmjs.org/regjsparser/-/regjsparser-0.1.5.tgz",
                     "integrity": "sha1-fuj4Tcb6eS0/0K4ijSS9lJ6tIFw=",
                     "requires": {
                         "jsesc": "~0.5.0"
@@ -2922,7 +2927,7 @@
             "dependencies": {
                 "globby": {
                     "version": "6.1.0",
-                    "resolved": "https://registry.npmjs.org/globby/-/globby-6.1.0.tgz",
+                    "resolved": "http://registry.npmjs.org/globby/-/globby-6.1.0.tgz",
                     "integrity": "sha1-9abXDoOV4hyFj7BInWTfAkJNUGw=",
                     "requires": {
                         "array-union": "^1.0.1",
@@ -2934,7 +2939,7 @@
                     "dependencies": {
                         "pify": {
                             "version": "2.3.0",
-                            "resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz",
+                            "resolved": "http://registry.npmjs.org/pify/-/pify-2.3.0.tgz",
                             "integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw="
                         }
                     }
@@ -2987,7 +2992,7 @@
         },
         "diffie-hellman": {
             "version": "5.0.3",
-            "resolved": "https://registry.npmjs.org/diffie-hellman/-/diffie-hellman-5.0.3.tgz",
+            "resolved": "http://registry.npmjs.org/diffie-hellman/-/diffie-hellman-5.0.3.tgz",
             "integrity": "sha512-kqag/Nl+f3GwyK25fhUMYj81BUOrZ9IuJsjIcDE5icNM9FJHAVm3VcUDxdLPoQtTuUylWm6ZIknYJwwaPxsUzg==",
             "requires": {
                 "bn.js": "^4.1.0",
@@ -3073,14 +3078,6 @@
                 "domelementtype": "1"
             }
         },
-        "dot-prop": {
-            "version": "4.2.0",
-            "resolved": "https://registry.npmjs.org/dot-prop/-/dot-prop-4.2.0.tgz",
-            "integrity": "sha512-tUMXrxlExSW6U2EXiiKGSBVdYgtV8qlHL+C10TsW4PURY/ic+eaysnSkwB4kA/mBlCyy/IKDJ+Lc3wbWeaXtuQ==",
-            "requires": {
-                "is-obj": "^1.0.0"
-            }
-        },
         "dotenv": {
             "version": "6.2.0",
             "resolved": "https://registry.npmjs.org/dotenv/-/dotenv-6.2.0.tgz",
@@ -3441,7 +3438,7 @@
             "dependencies": {
                 "array-flatten": {
                     "version": "1.1.1",
-                    "resolved": "https://registry.npmjs.org/array-flatten/-/array-flatten-1.1.1.tgz",
+                    "resolved": "http://registry.npmjs.org/array-flatten/-/array-flatten-1.1.1.tgz",
                     "integrity": "sha1-ml9pkFGx5wczKPKgCJaLZOopVdI="
                 },
                 "debug": {
@@ -3784,7 +3781,7 @@
                 },
                 "chalk": {
                     "version": "1.1.3",
-                    "resolved": "https://registry.npmjs.org/chalk/-/chalk-1.1.3.tgz",
+                    "resolved": "http://registry.npmjs.org/chalk/-/chalk-1.1.3.tgz",
                     "integrity": "sha1-qBFcVeSnAv5NFQq9OHKCKn4J/Jg=",
                     "requires": {
                         "ansi-styles": "^2.2.1",
@@ -3796,7 +3793,7 @@
                 },
                 "supports-color": {
                     "version": "2.0.0",
-                    "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-2.0.0.tgz",
+                    "resolved": "http://registry.npmjs.org/supports-color/-/supports-color-2.0.0.tgz",
                     "integrity": "sha1-U10EXOa2Nj+kARcIRimZXp3zJMc="
                 }
             }
@@ -4358,7 +4355,7 @@
                 },
                 "string-width": {
                     "version": "1.0.2",
-                    "resolved": "https://registry.npmjs.org/string-width/-/string-width-1.0.2.tgz",
+                    "resolved": "http://registry.npmjs.org/string-width/-/string-width-1.0.2.tgz",
                     "integrity": "sha1-EYvfW4zcUaKn5w0hHgfisLmxB9M=",
                     "requires": {
                         "code-point-at": "^1.0.0",
@@ -5037,7 +5034,7 @@
         },
         "is-accessor-descriptor": {
             "version": "0.1.6",
-            "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-0.1.6.tgz",
+            "resolved": "http://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-0.1.6.tgz",
             "integrity": "sha1-qeEss66Nh2cn7u84Q/igiXtcmNY=",
             "requires": {
                 "kind-of": "^3.0.2"
@@ -5091,7 +5088,7 @@
         },
         "is-data-descriptor": {
             "version": "0.1.4",
-            "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-0.1.4.tgz",
+            "resolved": "http://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-0.1.4.tgz",
             "integrity": "sha1-C17mSDiOLIYCgueT8YVv7D8wG1Y=",
             "requires": {
                 "kind-of": "^3.0.2"
@@ -5184,9 +5181,9 @@
             }
         },
         "is-obj": {
-            "version": "1.0.1",
-            "resolved": "http://registry.npmjs.org/is-obj/-/is-obj-1.0.1.tgz",
-            "integrity": "sha1-PkcprB9f3gJc19g6iW2rn09n2w8="
+            "version": "2.0.0",
+            "resolved": "https://registry.npmjs.org/is-obj/-/is-obj-2.0.0.tgz",
+            "integrity": "sha512-drqDG3cbczxxEJRoOXcOjtdp1J/lyp1mNn0xaznRs8+muBhgQcrnbspox5X5fOw0HnMnbfDzvnEMEtqDEJEo8w=="
         },
         "is-path-cwd": {
             "version": "2.2.0",
@@ -5292,9 +5289,9 @@
             "integrity": "sha1-R+Y/evVa+m+S4VAOaQ64uFKcCZo="
         },
         "jquery": {
-            "version": "3.5.0",
-            "resolved": "https://registry.npmjs.org/jquery/-/jquery-3.5.0.tgz",
-            "integrity": "sha512-Xb7SVYMvygPxbFMpTFQiHh1J7HClEaThguL15N/Gg37Lri/qKyhRGZYzHRyLH8Stq3Aow0LsHO2O2ci86fCrNQ=="
+            "version": "3.5.1",
+            "resolved": "https://registry.npmjs.org/jquery/-/jquery-3.5.1.tgz",
+            "integrity": "sha512-XwIBPqcMn57FxfT+Go5pzySnm4KWkT1Tv7gjrpT1srtf8Weynl6R273VJ5GjkRb51IzMp5nbaPjJXMWeju2MKg=="
         },
         "js-base64": {
             "version": "2.5.2",
@@ -5397,9 +5394,9 @@
             "integrity": "sha512-dcS1ul+9tmeD95T+x28/ehLgd9mENa3LsvDTtzm3vyBEO7RPptvAD+t44WVXaUjTBRcrpFeFlC8WCruUR456hw=="
         },
         "laravel-echo": {
-            "version": "1.8.0",
-            "resolved": "https://registry.npmjs.org/laravel-echo/-/laravel-echo-1.8.0.tgz",
-            "integrity": "sha512-hEHmNKUgV3fR2Do/2PKxfO3OiLmbjX89tahGEi4urS8JEuy/yoRtFToOJXV9ChtOpRqxo7trrygPOvXLwvc/6A=="
+            "version": "1.8.1",
+            "resolved": "https://registry.npmjs.org/laravel-echo/-/laravel-echo-1.8.1.tgz",
+            "integrity": "sha512-7IqPhPsIMesVCKBkjMlS2sD47STHykso95hhMYlN4sz0xLj80gt+L2VqrXkAuAivjQWP8yHH89EOtCGipawrhg=="
         },
         "laravel-mix": {
             "version": "4.1.4",
@@ -5506,7 +5503,7 @@
                 },
                 "pify": {
                     "version": "2.3.0",
-                    "resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz",
+                    "resolved": "http://registry.npmjs.org/pify/-/pify-2.3.0.tgz",
                     "integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw="
                 }
             }
@@ -5536,9 +5533,9 @@
             }
         },
         "lodash": {
-            "version": "4.17.15",
-            "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.15.tgz",
-            "integrity": "sha512-8xOcRHvCjnocdS5cpwXQXVzmmh5e5+saE2QGoeQmbKmRS6J3VQppPOIt0MnmE+4xlZoumy0GPG0D0MVIQbNA1A=="
+            "version": "4.17.19",
+            "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.19.tgz",
+            "integrity": "sha512-JNvd8XER9GQX0v2qJgsaN/mzFCNA5BRe/j8JN9d+tWyGLSodKQHKFicdwNYzWwI3wjRnaKPsGj1XkBjx/F96DQ=="
         },
         "lodash._baseassign": {
             "version": "3.2.0",
@@ -5733,7 +5730,7 @@
         },
         "media-typer": {
             "version": "0.3.0",
-            "resolved": "https://registry.npmjs.org/media-typer/-/media-typer-0.3.0.tgz",
+            "resolved": "http://registry.npmjs.org/media-typer/-/media-typer-0.3.0.tgz",
             "integrity": "sha1-hxDXrwqmJvj/+hzgAWhUUmMlV0g="
         },
         "mem": {
@@ -6030,7 +6027,7 @@
             "dependencies": {
                 "semver": {
                     "version": "5.3.0",
-                    "resolved": "https://registry.npmjs.org/semver/-/semver-5.3.0.tgz",
+                    "resolved": "http://registry.npmjs.org/semver/-/semver-5.3.0.tgz",
                     "integrity": "sha1-myzl094C0XxgEq0yaqa00M9U+U8="
                 }
             }
@@ -6123,7 +6120,7 @@
                 },
                 "chalk": {
                     "version": "1.1.3",
-                    "resolved": "https://registry.npmjs.org/chalk/-/chalk-1.1.3.tgz",
+                    "resolved": "http://registry.npmjs.org/chalk/-/chalk-1.1.3.tgz",
                     "integrity": "sha1-qBFcVeSnAv5NFQq9OHKCKn4J/Jg=",
                     "requires": {
                         "ansi-styles": "^2.2.1",
@@ -6153,7 +6150,7 @@
                 },
                 "supports-color": {
                     "version": "2.0.0",
-                    "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-2.0.0.tgz",
+                    "resolved": "http://registry.npmjs.org/supports-color/-/supports-color-2.0.0.tgz",
                     "integrity": "sha1-U10EXOa2Nj+kARcIRimZXp3zJMc="
                 },
                 "yallist": {
@@ -6858,14 +6855,29 @@
                 "vendors": "^1.0.0"
             },
             "dependencies": {
+                "is-obj": {
+                    "version": "2.0.0",
+                    "resolved": "https://registry.npmjs.org/is-obj/-/is-obj-2.0.0.tgz",
+                    "integrity": "sha512-drqDG3cbczxxEJRoOXcOjtdp1J/lyp1mNn0xaznRs8+muBhgQcrnbspox5X5fOw0HnMnbfDzvnEMEtqDEJEo8w=="
+                },
                 "postcss-selector-parser": {
-                    "version": "3.1.1",
-                    "resolved": "https://registry.npmjs.org/postcss-selector-parser/-/postcss-selector-parser-3.1.1.tgz",
-                    "integrity": "sha1-T4dfSvsMllc9XPTXQBGu4lCn6GU=",
+                    "version": "3.1.2",
+                    "resolved": "https://registry.npmjs.org/postcss-selector-parser/-/postcss-selector-parser-3.1.2.tgz",
+                    "integrity": "sha512-h7fJ/5uWuRVyOtkO45pnt1Ih40CEleeyCHzipqAZO2e5H20g25Y48uYnFUiShvY4rZWNJ/Bib/KVPmanaCtOhA==",
                     "requires": {
-                        "dot-prop": "^4.1.1",
+                        "dot-prop": "^5.2.0",
                         "indexes-of": "^1.0.1",
                         "uniq": "^1.0.1"
+                    },
+                    "dependencies": {
+                        "dot-prop": {
+                            "version": "5.2.0",
+                            "resolved": "https://registry.npmjs.org/dot-prop/-/dot-prop-5.2.0.tgz",
+                            "integrity": "sha512-uEUyaDKoSQ1M4Oq8l45hSE26SnTxL6snNnqvK/VWx5wJhmff5z0FUVJDKDanor/6w3kzE3i7XZOk+7wC0EXr1A==",
+                            "requires": {
+                                "is-obj": "^2.0.0"
+                            }
+                        }
                     }
                 }
             }
@@ -6935,14 +6947,29 @@
                 "postcss-selector-parser": "^3.0.0"
             },
             "dependencies": {
+                "is-obj": {
+                    "version": "2.0.0",
+                    "resolved": "https://registry.npmjs.org/is-obj/-/is-obj-2.0.0.tgz",
+                    "integrity": "sha512-drqDG3cbczxxEJRoOXcOjtdp1J/lyp1mNn0xaznRs8+muBhgQcrnbspox5X5fOw0HnMnbfDzvnEMEtqDEJEo8w=="
+                },
                 "postcss-selector-parser": {
-                    "version": "3.1.1",
-                    "resolved": "https://registry.npmjs.org/postcss-selector-parser/-/postcss-selector-parser-3.1.1.tgz",
-                    "integrity": "sha1-T4dfSvsMllc9XPTXQBGu4lCn6GU=",
+                    "version": "3.1.2",
+                    "resolved": "https://registry.npmjs.org/postcss-selector-parser/-/postcss-selector-parser-3.1.2.tgz",
+                    "integrity": "sha512-h7fJ/5uWuRVyOtkO45pnt1Ih40CEleeyCHzipqAZO2e5H20g25Y48uYnFUiShvY4rZWNJ/Bib/KVPmanaCtOhA==",
                     "requires": {
-                        "dot-prop": "^4.1.1",
+                        "dot-prop": "^5.2.0",
                         "indexes-of": "^1.0.1",
                         "uniq": "^1.0.1"
+                    },
+                    "dependencies": {
+                        "dot-prop": {
+                            "version": "5.2.0",
+                            "resolved": "https://registry.npmjs.org/dot-prop/-/dot-prop-5.2.0.tgz",
+                            "integrity": "sha512-uEUyaDKoSQ1M4Oq8l45hSE26SnTxL6snNnqvK/VWx5wJhmff5z0FUVJDKDanor/6w3kzE3i7XZOk+7wC0EXr1A==",
+                            "requires": {
+                                "is-obj": "^2.0.0"
+                            }
+                        }
                     }
                 }
             }
@@ -7498,7 +7525,7 @@
                 },
                 "pify": {
                     "version": "2.3.0",
-                    "resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz",
+                    "resolved": "http://registry.npmjs.org/pify/-/pify-2.3.0.tgz",
                     "integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw="
                 }
             }
@@ -7533,7 +7560,7 @@
         },
         "readable-stream": {
             "version": "2.3.6",
-            "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.6.tgz",
+            "resolved": "http://registry.npmjs.org/readable-stream/-/readable-stream-2.3.6.tgz",
             "integrity": "sha512-tQtKA9WIAhBF3+VLAseyMqZeBjW0AHJoxOtYqSUZNJxauErmLbVm2FW1y+J/YA9dUrAC39ITejlZWhVIwawkKw==",
             "requires": {
                 "core-util-is": "~1.0.0",
@@ -7654,7 +7681,7 @@
             "dependencies": {
                 "jsesc": {
                     "version": "0.5.0",
-                    "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-0.5.0.tgz",
+                    "resolved": "http://registry.npmjs.org/jsesc/-/jsesc-0.5.0.tgz",
                     "integrity": "sha1-597mbjXW/Bb3EP6R1c9p9w8IkR0="
                 }
             }
@@ -7835,7 +7862,7 @@
             "dependencies": {
                 "convert-source-map": {
                     "version": "0.3.5",
-                    "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-0.3.5.tgz",
+                    "resolved": "http://registry.npmjs.org/convert-source-map/-/convert-source-map-0.3.5.tgz",
                     "integrity": "sha1-8dgClQr33SYxof6+BZZVDIarMZA=",
                     "dev": true
                 }
@@ -7901,9 +7928,9 @@
             "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg=="
         },
         "sass": {
-            "version": "1.26.5",
-            "resolved": "https://registry.npmjs.org/sass/-/sass-1.26.5.tgz",
-            "integrity": "sha512-FG2swzaZUiX53YzZSjSakzvGtlds0lcbF+URuU9mxOv7WBh7NhXEVDa4kPKN4hN6fC2TkOTOKqiqp6d53N9X5Q==",
+            "version": "1.26.10",
+            "resolved": "https://registry.npmjs.org/sass/-/sass-1.26.10.tgz",
+            "integrity": "sha512-bzN0uvmzfsTvjz0qwccN1sPm2HxxpNI/Xa+7PlUEMS+nQvbyuEK7Y0qFqxlPHhiNHb1Ze8WQJtU31olMObkAMw==",
             "dev": true,
             "requires": {
                 "chokidar": ">=2.0.0 <4.0.0"
@@ -8022,7 +8049,7 @@
             "dependencies": {
                 "source-map": {
                     "version": "0.4.4",
-                    "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.4.4.tgz",
+                    "resolved": "http://registry.npmjs.org/source-map/-/source-map-0.4.4.tgz",
                     "integrity": "sha1-66T12pwNyZneaAMti092FzZSA2s=",
                     "requires": {
                         "amdefine": ">=0.0.4"
@@ -8189,7 +8216,7 @@
         },
         "sha.js": {
             "version": "2.4.11",
-            "resolved": "https://registry.npmjs.org/sha.js/-/sha.js-2.4.11.tgz",
+            "resolved": "http://registry.npmjs.org/sha.js/-/sha.js-2.4.11.tgz",
             "integrity": "sha512-QMEp5B7cftE7APOjk5Y6xgrbWu+WkLVQwk8JNjZ8nKRciZaByEW6MubieAiToS7+dwvrjGhH8jRXz3MVd0AYqQ==",
             "requires": {
                 "inherits": "^2.0.1",
@@ -8770,13 +8797,23 @@
             },
             "dependencies": {
                 "postcss-selector-parser": {
-                    "version": "3.1.1",
-                    "resolved": "https://registry.npmjs.org/postcss-selector-parser/-/postcss-selector-parser-3.1.1.tgz",
-                    "integrity": "sha1-T4dfSvsMllc9XPTXQBGu4lCn6GU=",
+                    "version": "3.1.2",
+                    "resolved": "https://registry.npmjs.org/postcss-selector-parser/-/postcss-selector-parser-3.1.2.tgz",
+                    "integrity": "sha512-h7fJ/5uWuRVyOtkO45pnt1Ih40CEleeyCHzipqAZO2e5H20g25Y48uYnFUiShvY4rZWNJ/Bib/KVPmanaCtOhA==",
                     "requires": {
-                        "dot-prop": "^4.1.1",
+                        "dot-prop": "^5.2.0",
                         "indexes-of": "^1.0.1",
                         "uniq": "^1.0.1"
+                    },
+                    "dependencies": {
+                        "dot-prop": {
+                            "version": "5.2.0",
+                            "resolved": "https://registry.npmjs.org/dot-prop/-/dot-prop-5.2.0.tgz",
+                            "integrity": "sha512-uEUyaDKoSQ1M4Oq8l45hSE26SnTxL6snNnqvK/VWx5wJhmff5z0FUVJDKDanor/6w3kzE3i7XZOk+7wC0EXr1A==",
+                            "requires": {
+                                "is-obj": "^2.0.0"
+                            }
+                        }
                     }
                 }
             }
@@ -9026,7 +9063,7 @@
         },
         "tty-browserify": {
             "version": "0.0.0",
-            "resolved": "https://registry.npmjs.org/tty-browserify/-/tty-browserify-0.0.0.tgz",
+            "resolved": "http://registry.npmjs.org/tty-browserify/-/tty-browserify-0.0.0.tgz",
             "integrity": "sha1-oVe6QC2iTpv5V/mqadUk7tQpAaY="
         },
         "tunnel-agent": {
@@ -9396,9 +9433,9 @@
             }
         },
         "vue-loading-overlay": {
-            "version": "3.3.2",
-            "resolved": "https://registry.npmjs.org/vue-loading-overlay/-/vue-loading-overlay-3.3.2.tgz",
-            "integrity": "sha512-5nBsaeb3quOBVXCgbSu9VNWkBVEsbDCupahv8dqkgbtJ00uKoNOPyw38+reWGHKNDBDl+x7x8wT8u3dV7ali7g=="
+            "version": "3.3.3",
+            "resolved": "https://registry.npmjs.org/vue-loading-overlay/-/vue-loading-overlay-3.3.3.tgz",
+            "integrity": "sha512-wq07DyzqAtQ7A5Q1VPNMGhFLlSWTGAEdzhXgJqN4Xbr/RKpUYvW3EsdRIiwBXKawracJwnV4lTpqS8HrjI20iA=="
         },
         "vue-masonry-css": {
             "version": "1.0.3",
@@ -9439,9 +9476,9 @@
             }
         },
         "vue-tribute": {
-            "version": "1.0.4",
-            "resolved": "https://registry.npmjs.org/vue-tribute/-/vue-tribute-1.0.4.tgz",
-            "integrity": "sha512-wkvmBxpXWdWCHsyiTMObRenRwbsYqe30avvM7sD4gocEY8eYKGT4J17Z8RMUwrTNckUmwsZXvBzA/q8wh/eBeA=="
+            "version": "1.0.6",
+            "resolved": "https://registry.npmjs.org/vue-tribute/-/vue-tribute-1.0.6.tgz",
+            "integrity": "sha512-k84Cm3EOCTOpRLfgl4Ze/8nINNDEMO00UAVZyAcghipEafSDu4GBYAvuOyMPZ1shFOIJXc4Ej/AywP/CuMuwvQ=="
         },
         "watchpack": {
             "version": "1.7.2",

+ 10 - 9
package.json

@@ -12,25 +12,26 @@
     },
     "devDependencies": {
         "axios": "^0.18.1",
-        "bootstrap": "^4.5.0",
+        "bootstrap": "^4.5.2",
         "cross-env": "^5.2.1",
-        "jquery": "^3.5.0",
-        "lodash": ">=4.17.13",
+        "jquery": "^3.5.1",
+        "lodash": "^4.17.19",
         "popper.js": "^1.16.1",
         "resolve-url-loader": "^2.3.2",
-        "sass": "^1.26.5",
+        "sass": "^1.26.10",
         "sass-loader": "^7.3.1",
         "vue": "^2.6.11",
         "vue-masonry-css": "^1.0.3",
         "vue-template-compiler": "^2.6.11"
     },
     "dependencies": {
-        "@trevoreyre/autocomplete-vue": "^2.1.1",
-        "bootstrap-vue": "^2.14.0",
+        "@trevoreyre/autocomplete-vue": "^2.2.0",
+        "animate.css": "^4.1.0",
+        "bootstrap-vue": "^2.16.0",
         "filesize": "^3.6.1",
         "howler": "^2.2.0",
         "infinite-scroll": "^3.0.6",
-        "laravel-echo": "^1.8.0",
+        "laravel-echo": "^1.8.1",
         "laravel-mix": "^4.1.4",
         "node-sass": "^4.14.1",
         "promise-polyfill": "8.1.0",
@@ -43,9 +44,9 @@
         "vue-content-loader": "^0.2.3",
         "vue-cropperjs": "^4.1.0",
         "vue-infinite-loading": "^2.4.5",
-        "vue-loading-overlay": "^3.3.2",
+        "vue-loading-overlay": "^3.3.3",
         "vue-timeago": "^5.1.2",
-        "vue-tribute": "^1.0.4",
+        "vue-tribute": "^1.0.6",
         "zuck.js": "^1.6.0"
     },
     "collective": {

BIN
public/css/app.css


BIN
public/css/appdark.css


BIN
public/css/landing.css


BIN
public/js/components.js


BIN
public/js/compose.js


BIN
public/js/search.js


BIN
public/js/status.js


BIN
public/js/timeline.js


BIN
public/js/vendor.js


BIN
public/mix-manifest.json


+ 14 - 2
resources/assets/js/components/PostComponent.vue

@@ -859,7 +859,9 @@ export default {
                   }
                 }
                 this.loaded = true;
-                this.fetchProfilePosts();
+                setTimeout(function() {
+                  self.fetchProfilePosts();
+                }, 3000);
                 setTimeout(function() {
                   document.querySelectorAll('.status-comment .comment-text a').forEach(function(i, e) { 
                     if(i.href.startsWith(window.location.origin)) {
@@ -947,12 +949,16 @@ export default {
           } else {
             this.reactions.liked = true;
             let user = this.user;
-            this.likes.push(user);
+            this.likes.unshift(user);
+            setTimeout(function() {
+              event.target.classList.add('animate__animated', 'animate__bounce');
+            },100);
           }
         }).catch(err => {
           console.error(err);
           swal('Error', 'Something went wrong, please try again later.', 'error');
         });
+        window.navigator.vibrate(200);
       },
 
       shareStatus() {
@@ -1383,6 +1389,9 @@ export default {
       },
 
       fetchProfilePosts() {
+        if(!$('body').hasClass('loggedIn') && this.loaded) {
+          return;
+        }
         let self = this;
         let apiUrl = '/api/pixelfed/v1/accounts/' + this.statusProfileId + '/statuses';
         axios.get(apiUrl, {
@@ -1426,6 +1435,9 @@ export default {
       },
 
       showTaggedPeopleModal() {
+        if(!$('body').hasClass('loggedIn') && this.loaded) {
+          return;
+        }
         this.$refs.taggedModal.show();
       },
 

+ 105 - 3
resources/assets/js/components/SearchResults.vue

@@ -11,10 +11,57 @@
 
 	<div v-if="!loading && !networkError" class="mt-5">
 		<div v-if="analysis == 'all'" class="row">
-			<div class="col-12 mb-5">
+			<div class="col-12 d-flex justify-content-between align-items-center">
 				<p class="h5 font-weight-bold text-dark">Showing results for <i>{{query}}</i></p>
+				<div v-if="placesSearchEnabled" title="Show Places" data-toggle="tooltip">
+					<span v-if="results.placesPagination.total > 0" class="badge badge-light mr-2 p-1 border" style="margin-top:-5px;">{{formatCount(results.placesPagination.total)}}</span>
+					<div class="d-inline custom-control custom-switch">
+						<input type="checkbox" class="custom-control-input" id="placesSwitch" v-model="showPlaces">
+						<label class="custom-control-label font-weight-bold text-sm text-lighter" for="placesSwitch"><i class="fas fa-map-marker-alt"></i></label>
+					</div>
+				</div>
+			</div>
+			<div class="col-12 mb-5">
 				<hr>
 			</div>
+			<div v-if="placesSearchEnabled && showPlaces" class="col-12">
+				<div class="mb-4">
+					<p class="text-secondary small font-weight-bold">PLACES <span class="pl-1 text-lighter">({{results.placesPagination.total}})</span></p>
+				</div>
+				<div v-if="results.places.length" class="mb-5">
+					<a v-for="(hashtag, index) in results.places" class="mr-3 pr-4 d-inline-block text-decoration-none" :href="buildUrl('places', hashtag)">
+						<div class="pb-2">
+							<div class="media align-items-center py-2">
+								<div class="media-body text-truncate">
+									<p class="mb-0 text-truncate text-dark font-weight-bold" data-toggle="tooltip" :title="hashtag.value">
+										<i class="fas fa-map-marker-alt text-lighter mr-2"></i> {{hashtag.value}}
+									</p>
+								</div>
+							</div>
+						</div>
+					</a>
+					<p v-if="results.places.length == 20 || placesCursor > 0" class="text-center mt-3">
+						<a v-if="placesCursor == 1" href="#" class="btn btn-outline-secondary btn-sm font-weight-bold py-0 disabled" disabled>
+							<i class="fas fa-chevron-left mr-2"></i> Previous
+						</a>
+						<a v-else href="#" @click.prevent="placesPrevPage()" class="btn btn-outline-secondary btn-sm font-weight-bold py-0">
+							<i class="fas fa-chevron-left mr-2"></i> Previous
+						</a>
+
+						<span class="mx-4 small text-lighter">{{placesCursor}}/{{results.placesPagination.last_page}}</span>
+
+						<a v-if="placesCursor !== results.placesPagination.last_page" @click.prevent="placesNextPage()" href="#" class="btn btn-primary btn-sm font-weight-bold py-0">
+							Next <i class="fas fa-chevron-right ml-2"></i>
+						</a>
+						<a v-else href="#" class="btn btn-primary btn-sm font-weight-bold py-0 disabled" disabled>
+							Next <i class="fas fa-chevron-right ml-2"></i>
+						</a>
+					</p>
+				</div>
+				<div v-else>
+					<div class="border py-3 text-center font-weight-bold">No results found</div>
+				</div>			
+			</div>
 			<div class="col-md-3">
 				<div class="mb-4">
 					<p class="text-secondary small font-weight-bold">HASHTAGS <span class="pl-1 text-lighter">({{results.hashtags.length}})</span></p>
@@ -284,7 +331,8 @@ export default {
 			results: {
 				hashtags: [],
 				profiles: [],
-				statuses: []
+				statuses: [],
+				places: [],
 			},
 			filters: {
 				hashtags: true,
@@ -292,6 +340,10 @@ export default {
 				statuses: true
 			},
 			analysis: 'profile',
+			showPlaces: false,
+			placesCursor: 1,
+			placesCache: [],
+			placesSearchEnabled: false
 		}
 	},
 	beforeMount() {
@@ -300,6 +352,9 @@ export default {
 	mounted() {
 		$('.search-bar input').val(this.query);
 	},
+	updated() {
+		$('[data-toggle="tooltip"]').tooltip();
+	},
 	methods: {
 		bootSearch() {
 			let lexer = this.searchLexer();
@@ -388,7 +443,7 @@ export default {
 						params: {
 							'q': this.query,
 							'src': 'metro',
-							'v': 1,
+							'v': 2,
 							'scope': 'all'
 						}
 					}).then(res => {
@@ -396,6 +451,9 @@ export default {
 						this.results.hashtags = results.hashtags ? results.hashtags : [];
 						this.results.profiles = results.profiles ? results.profiles : [];
 						this.results.statuses = results.posts ? results.posts : [];
+						this.results.places   = results.places ? results.places : [];
+						this.placesCache = results.places;
+						this.results.placesPagination   = results.placesPagination ? results.placesPagination : [];
 						this.loading = false;
 					}).catch(err => {
 						this.loading = false;
@@ -500,6 +558,50 @@ export default {
 					this.networkError = true;
 				break;
 			}
+		},
+
+		placesPrevPage() {
+			this.placesCursor--;
+			if(this.placesCursor == 1) {
+				this.results.places = this.placesCache.slice(0, 20);
+				return;
+			}
+			let plc = this.placesCursor * 20;
+			this.results.places = this.placesCache.slice(plc, 20);
+			return;
+		},
+
+		placesNextPage() {
+			this.placesCursor++;
+			let plc = this.placesCursor * 20;
+			if(this.placesCache.length > 20) {
+				this.results.places = this.placesCache.slice(this.placesCursor == 1 ? 0 : plc, 20);
+				return;
+			} 
+			axios.get('/api/search', {
+				params: {
+					'q': this.query,
+					'src': 'metro',
+					'v': 2,
+					'scope': 'all',
+					'page': this.placesCursor
+				}
+			}).then(res => {
+				let results = res.data;
+				this.results.places = results.places ? results.places : [];
+				this.placesCache.push(...results.places);
+				this.loading = false;
+			}).catch(err => {
+				this.loading = false;
+				console.log(err);
+				this.networkError = true;
+			});
+
+		},
+
+		formatCount(num) {
+			let count = window.App.util.format.count(num);
+			return count;
 		}
 	}
 

+ 11 - 4
resources/assets/js/components/Timeline.vue

@@ -162,7 +162,8 @@
 
 						<div class="card-body">
 							<div v-if="!modes.distractionFree" class="reactions my-1 pb-2">
-								<h3 v-bind:class="[status.favourited ? 'fas fa-heart text-danger pr-3 m-0 cursor-pointer' : 'far fa-heart pr-3 m-0 like-btn text-lighter cursor-pointer']" title="Like" v-on:click="likeStatus(status, $event)"></h3>
+								<h3 v-if="status.favourited" class="fas fa-heart text-danger pr-3 m-0 cursor-pointer" title="Like" v-on:click="likeStatus(status, $event);"></h3>
+								<h3 v-else class="far fa-heart pr-3 m-0 like-btn text-lighter cursor-pointer" title="Like" v-on:click="likeStatus(status, $event);"></h3>
 								<h3 v-if="!status.comments_disabled" class="far fa-comment text-lighter pr-3 m-0 cursor-pointer" title="Comment" v-on:click="commentFocus(status, $event)"></h3>
 								<h3 v-if="status.visibility == 'public'" v-bind:class="[status.reblogged ? 'fas fa-retweet pr-3 m-0 text-primary cursor-pointer' : 'fas fa-retweet pr-3 m-0 text-lighter share-btn cursor-pointer']" title="Share" v-on:click="shareStatus(status, $event)"></h3>
 								<h3 class="fas fa-expand pr-3 m-0 cursor-pointer text-lighter" v-on:click="lightbox(status)"></h3>
@@ -196,7 +197,7 @@
 											<span v-html="reply.content" style="word-break: break-all;" class="comment-body"></span>
 										</span>
 										<span class="mb-0" style="min-width:38px">
-											<span v-on:click="likeStatus(reply, $event)">
+											<span v-on:click="likeStatus(reply, $event);">
 												<i v-bind:class="[reply.favourited ? 'fas fa-heart fa-sm text-danger cursor-pointer':'far fa-heart fa-sm text-lighter cursor-pointer']"></i>
 											</span>
 											<!-- <post-menu :status="reply" :profile="profile" size="sm" :modal="'true'" :feed="feed" class="d-inline-flex pl-2"></post-menu> -->
@@ -411,7 +412,7 @@
 						<div class="ml-3">
 							<p class="mb-0">
 								<span v-if="statusOwner(s)" class="font-weight-bold small">{{s.favourites_count == 1 ? '1 like' : s.favourites_count+' likes'}}</span>
-								<span class="px-2"><i v-bind:class="[s.favourited ? 'fas fa-heart text-danger cursor-pointer' : 'far fa-heart like-btn text-lighter cursor-pointer']" v-on:click="likeStatus(s, $event)"></i></span>
+								<span class="px-2"><i v-bind:class="[s.favourited ? 'fas fa-heart text-danger cursor-pointer' : 'far fa-heart like-btn text-lighter cursor-pointer']" v-on:click="likeStatus(s, $event);"></i></span>
 								<span class="mr-2 cursor-pointer"><i class="fas fa-ellipsis-v" @click="ctxMenu(s)"></i></span>
 							</p>
 						</div>
@@ -922,7 +923,7 @@
 
 			},
 
-			likeStatus(status) {
+			likeStatus(status, event) {
 				if($('body').hasClass('loggedIn') == false) {
 					return;
 				}
@@ -937,6 +938,12 @@
 					status.favourites_count = count;
 					swal('Error', 'Something went wrong, please try again later.', 'error');
 				});
+				window.navigator.vibrate(200);
+				if(status.favourited) {
+					setTimeout(function() {
+						event.target.classList.add('animate__animated', 'animate__bounce');
+					},100);
+				}
 			},
 
 			shareStatus(status, $event) {

+ 3 - 1
resources/assets/sass/app.scss

@@ -21,4 +21,6 @@
 
 @import '~bootstrap-vue/dist/bootstrap-vue.css';
 
-@import "moment";
+@import "moment";
+
+@import '~animate.css/animate.min.css';

+ 27 - 28
resources/views/status/embed.blade.php

@@ -63,36 +63,32 @@
         </div>
         @endif
       @break
-      @case('album')
-        @if($status->is_nsfw)
-
-        @else
-          <div id="photo-carousel-wrapper-{{$status->id}}" class="carousel slide carousel-fade" data-ride="carousel">
-            <ol class="carousel-indicators">
-              @for($i = 0; $i < $status->media_count; $i++)
-              <li data-target="#photo-carousel-wrapper-{{$status->id}}" data-slide-to="{{$i}}" class="{{$i == 0 ? 'active' : ''}}"></li>
-              @endfor
-            </ol>
-            <div class="carousel-inner">
-              @foreach($status->media()->orderBy('order')->get() as $media)
-              <div class="carousel-item {{$loop->iteration == 1 ? 'active' : ''}}">
-                <figure class="{{$media->filter_class}}">
-                  <span class="float-right mr-3 badge badge-dark" style="position:fixed;top:8px;right:0;margin-bottom:-20px;">{{$loop->iteration}}/{{$loop->count}}</span>
-                  <img class="d-block w-100" src="{{$media->url()}}" alt="{{$status->caption}}">
-                </figure>
-              </div>
-              @endforeach
+      @case('photo:album')
+        <div id="photo-carousel-wrapper-{{$status->id}}" class="carousel slide carousel-fade mb-n3 " data-ride="carousel">
+          <ol class="carousel-indicators">
+            @for($i = 0; $i < $status->media_count; $i++)
+            <li data-target="#photo-carousel-wrapper-{{$status->id}}" data-slide-to="{{$i}}" class="{{$i == 0 ? 'active' : ''}}"></li>
+            @endfor
+          </ol>
+          <div class="carousel-inner">
+            @foreach($status->media()->orderBy('order')->get() as $media)
+            <div class="carousel-item {{$loop->iteration == 1 ? 'active' : ''}}">
+              <figure class="{{$media->filter_class}}">
+                <div class="float-right mr-3 badge badge-dark border border-secondary rounded-pill p-2" style="position:absolute;top:8px;right:0;margin-bottom:-20px;">{{$loop->iteration}}/{{$loop->count}}</div>
+                <img class="d-block w-100" src="{{$media->url()}}" alt="{{$status->caption}}">
+              </figure>
             </div>
-            <a class="carousel-control-prev" href="#photo-carousel-wrapper-{{$status->id}}" role="button" data-slide="prev">
-              <span class="carousel-control-prev-icon" aria-hidden="true"></span>
-              <span class="sr-only">Previous</span>
-            </a>
-            <a class="carousel-control-next" href="#photo-carousel-wrapper-{{$status->id}}" role="button" data-slide="next">
-              <span class="carousel-control-next-icon" aria-hidden="true"></span>
-              <span class="sr-only">Next</span>
-            </a>
+            @endforeach
           </div>
-        @endif
+          <a class="carousel-control-prev" href="#photo-carousel-wrapper-{{$status->id}}" role="button" data-slide="prev">
+            <span class="carousel-control-prev-icon" aria-hidden="true"></span>
+            <span class="sr-only">Previous</span>
+          </a>
+          <a class="carousel-control-next" href="#photo-carousel-wrapper-{{$status->id}}" role="button" data-slide="next">
+            <span class="carousel-control-next-icon" aria-hidden="true"></span>
+            <span class="sr-only">Next</span>
+          </a>
+        </div>
       @break
       @case('video')
         @if($status->is_nsfw)
@@ -174,5 +170,8 @@
   </div>
   <script type="text/javascript">window.addEventListener("message",e=>{const t=e.data||{};window.parent&&"setHeight"===t.type&&window.parent.postMessage({type:"setHeight",id:t.id,height:document.getElementsByTagName("html")[0].scrollHeight},"*")});</script>
   <script type="text/javascript">document.querySelectorAll('.caption-container a').forEach(function(i) {i.setAttribute('target', '_blank');});</script>
+    <script type="text/javascript" src="{{ mix('js/manifest.js') }}"></script>
+    <script type="text/javascript" src="{{ mix('js/vendor.js') }}"></script>
+    <script type="text/javascript" src="{{ mix('js/app.js') }}"></script>
 </body>
 </html>