Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Implemented user media manager #262

Merged
merged 8 commits into from
Mar 13, 2021
Merged
Show file tree
Hide file tree
Changes from 7 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions extend.php
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@

return [
(new Extend\Routes('api'))
->get('/fof/uploads', 'fof-upload.list', Api\Controllers\ListUploadsController::class)
->post('/fof/upload', 'fof-upload.upload', Api\Controllers\UploadController::class)
->post('/fof/watermark', 'fof-upload.watermark', Api\Controllers\WatermarkUploadController::class)
->get('/fof/download/{uuid}/{post}/{csrf}', 'fof-upload.download', Api\Controllers\DownloadController::class),
Expand All @@ -30,6 +31,8 @@
(new Extend\Frontend('forum'))
->css(__DIR__.'/resources/less/forum/download.less')
->css(__DIR__.'/resources/less/forum/upload.less')
->css(__DIR__.'/resources/less/forum/fileManagerModal.less')
->css(__DIR__.'/resources/less/forum/fileList.less')
->js(__DIR__.'/js/dist/forum.js'),
new Extend\Locales(__DIR__.'/resources/locale'),

Expand Down
717 changes: 716 additions & 1 deletion js/dist/admin.js

Large diffs are not rendered by default.

2 changes: 1 addition & 1 deletion js/dist/admin.js.map

Large diffs are not rendered by default.

1,486 changes: 1,485 additions & 1 deletion js/dist/forum.js

Large diffs are not rendered by default.

2 changes: 1 addition & 1 deletion js/dist/forum.js.map

Large diffs are not rendered by default.

19 changes: 19 additions & 0 deletions js/src/admin/components/UploadPage.js
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,7 @@ export default class UploadPage extends ExtensionPage {
'cdnUrl',
'maxFileSize',
'whitelistedClientExtensions',
'composerButtonVisiblity',
// watermark
'watermark',
'watermarkPosition',
Expand Down Expand Up @@ -62,6 +63,13 @@ export default class UploadPage extends ExtensionPage {
bottom: 'bottom',
};

// Composer button options
this.composerButtonVisiblityOptions = {
'both' : app.translator.trans('fof-upload.admin.labels.composer_buttons.options.both'),
'upload-btn' : app.translator.trans('fof-upload.admin.labels.composer_buttons.options.upload-btn'),
'media-btn' : app.translator.trans('fof-upload.admin.labels.composer_buttons.options.media-btn')
}

// get the saved settings from the database
const settings = app.data.settings;

Expand Down Expand Up @@ -193,6 +201,17 @@ export default class UploadPage extends ExtensionPage {
m('.helpText', app.translator.trans('fof-upload.admin.help_texts.download_templates')),
this.templateOptionsDescriptions(),
]),
m('fieldset', [
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Non-blocking, but we should probably change this stuff to JSX for better readability in another PR.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Agreed, but as you say, this should be a separate PR to this feature

m('legend', app.translator.trans('fof-upload.admin.labels.composer_buttons.title')),
m('.helpText', app.translator.trans('fof-upload.admin.help_texts.composer_buttons')),
m('div', [
Select.component({
jaspervriends marked this conversation as resolved.
Show resolved Hide resolved
options: this.composerButtonVisiblityOptions,
onchange: this.values.composerButtonVisiblity,
value: this.values.composerButtonVisiblity() || 'both',
}),
])
]),
m('fieldset', [
m('legend', app.translator.trans('fof-upload.admin.labels.resize.title')),
m('.helpText', app.translator.trans('fof-upload.admin.help_texts.resize')),
Expand Down
19 changes: 19 additions & 0 deletions js/src/common/fileToBBcode.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
export default function fileToBBcode(file) {
switch (file.tag()) {
// File
case 'file':
return `[upl-file uuid=${file.uuid()} size=${file.humanSize()}]${file.baseName()}[/upl-file]`;

// Image template
case 'image':
return `[upl-image uuid=${file.uuid()} size=${file.humanSize()} url=${file.url()}]${file.baseName()}[/upl-image]`;

// Image preview
case 'image-preview':
return `[upl-image-preview url=${file.url()}]`;

// 'just-url' or unknown
default:
return file.url();
}
}
41 changes: 41 additions & 0 deletions js/src/common/mimeToIcon.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
const image = ['image/png', 'image/jpg', 'image/jpeg', 'image/svg+xml'];
const archive = ['application/zip', 'application/x-7z-compressed', 'application/gzip', 'application/vnd.rar', 'application/x-rar-compressed'];
const code = ['text/html', 'text/css', 'text/javascript', 'application/json', 'application/ld+json', 'text/javascript', 'application/x-httpd-php'];
const word = ['application/x-abiword', 'application/msword', 'application/vnd.openxmlformats-officedocument.wordprocessingml.document'];

export default function mimeToIcon(fileType) {
// Display image (do not display for)
if (image.indexOf(fileType) >= 0) {
return 'image';
}
// Display image icon for other types
else if (fileType.includes('image/')) {
return 'far fa-file-image';
}
// Video icon
else if (fileType.includes('video/')) {
return 'far fa-file-video';
}
// Archive icon
else if (archive.indexOf(fileType) >= 0) {
return 'far fa-file-archive';
}
// PDF icon
else if (fileType === 'application/pdf') {
return 'far fa-file-pdf';
}
// Word
else if (word.indexOf(fileType) >= 0) {
return 'far fa-file-word';
}
// Audio icon
else if (fileType.includes('audio/')) {
return 'far fa-file-audio';
}
// Code files
else if (code.indexOf(fileType) >= 0) {
return 'far fa-file-code';
}

return 'far fa-file';
}
29 changes: 29 additions & 0 deletions js/src/common/models/File.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
import Model from 'flarum/Model';
import mixin from 'flarum/utils/mixin';
import fileToBBcode from '../fileToBBcode';

export default class File extends mixin(Model, {
baseName: Model.attribute('baseName'),
path: Model.attribute('path'),
url: Model.attribute('url'),
type: Model.attribute('type'),
size: Model.attribute('size'),
humanSize: Model.attribute('humanSize'),
createdAt: Model.attribute('createdAt'),
uuid: Model.attribute('uuid'),
tag: Model.attribute('tag'),
}) {
/**
* Use FoF Uploads endpoint
*/
apiEndpoint() {
return '/fof/uploads' + (this.exists ? '/' + this.data.id : '');
}

/**
* Generate bbcode for this file
*/
bbcode() {
return fileToBBcode(this);
}
}
34 changes: 26 additions & 8 deletions js/src/forum/addUploadButton.js
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ import UploadButton from './components/UploadButton';
import DragAndDrop from './components/DragAndDrop';
import PasteClipboard from './components/PasteClipboard';
import Uploader from './handler/Uploader';
import FileManagerButton from './components/FileManagerButton';

export default function () {
extend(TextEditor.prototype, 'oninit', function () {
Expand All @@ -13,19 +14,36 @@ export default function () {
extend(TextEditor.prototype, 'controlItems', function (items) {
if (!app.forum.attribute('fof-upload.canUpload')) return;

items.add(
'fof-upload',
UploadButton.component({
uploader: this.uploader,
})
);
const composerButtonVisiblity = app.forum.attribute("fof-upload.composerButtonVisiblity");

// Add media button
if(composerButtonVisiblity === "both" || composerButtonVisiblity === "media-btn") {
items.add(
'fof-upload-media',
FileManagerButton.component({
uploader: this.uploader,
})
);
}

// Add upload button
if(composerButtonVisiblity === "both" || composerButtonVisiblity === "upload-btn") {
items.add(
'fof-upload',
UploadButton.component({
uploader: this.uploader,
})
);
}
});

extend(TextEditor.prototype, 'oncreate', function (f_, vnode) {
if (!app.forum.attribute('fof-upload.canUpload')) return;

this.uploader.on('success', (image) => {
this.attrs.composer.editor.insertAtCursor(image + '\n');
this.uploader.on('success', ({ file, addBBcode }) => {
if (!addBBcode) return;

this.attrs.composer.editor.insertAtCursor(file.bbcode() + '\n');

// We wrap this in a typeof check to prevent it running when a user
// is creating a new discussion. There's nothing to preview in a new
Expand Down
12 changes: 2 additions & 10 deletions js/src/forum/components/DragAndDrop.js
Original file line number Diff line number Diff line change
Expand Up @@ -16,8 +16,6 @@ export default class DragAndDrop {
this.composerElement.addEventListener('dragend', this.handlers.out);

this.composerElement.addEventListener('drop', (this.handlers.dropping = this.dropping.bind(this)));

this.isDropping = this.over = false;
}

supportsFileDragging() {
Expand Down Expand Up @@ -88,14 +86,8 @@ export default class DragAndDrop {

event.preventDefault();

if (!this.isDropping) {
this.isDropping = true;
this.composerElement.classList.add('fof-upload-dropping');
this.upload(event.dataTransfer.files);

this.upload(event.dataTransfer.files, () => {
this.composerElement.classList.remove('fof-upload-dropping');
this.isDropping = false;
});
}
this.composerElement.classList.remove('fof-upload-dragging');
}
}
41 changes: 41 additions & 0 deletions js/src/forum/components/FileManagerButton.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
import app from 'flarum/app';
import Component from 'flarum/Component';
import Button from 'flarum/components/Button';
import FileManagerModal from './FileManagerModal';

export default class FileManagerButton extends Component {
view() {
return Button.component({
className: 'Button fof-upload-button Button--icon',
onclick: this.fileManagerButtonClicked.bind(this),
icon: 'fas fa-photo-video',
title: app.translator.trans('fof-upload.forum.buttons.media'),
});
}

/**
* Show tooltip on hover
*
* @param {*} vnode
*/
oncreate(vnode) {
super.oncreate(vnode);

// Add tooltip
this.$().tooltip();
}

/**
* Event handler for upload button being clicked
*
* @param {PointerEvent} e
*/
fileManagerButtonClicked(e) {
e.preventDefault();

// Open dialog
app.modal.show(FileManagerModal, {
uploader: this.attrs.uploader
});
}
}
Loading