discourse/plugins/chat/assets/javascripts/discourse/components/chat-composer-uploads.js
Joffrey JAFFEUX 84c1cc70d6
REFACTOR: naming and state refactor (#19187)
- better handling of drawer state using chat state manager
- removes various float and topic occurrences to use drawer
- ensures user can chat before doing a lot of chat setup
- fixes a bug which was creating presence errors in tests
- removes dead code
2022-11-25 14:15:38 +01:00

131 lines
3.6 KiB
JavaScript

import Component from "@ember/component";
import { clipboardHelpers } from "discourse/lib/utilities";
import { action } from "@ember/object";
import { inject as service } from "@ember/service";
import UppyMediaOptimization from "discourse/lib/uppy-media-optimization-plugin";
import discourseComputed, { bind } from "discourse-common/utils/decorators";
import UppyUploadMixin from "discourse/mixins/uppy-upload";
export default Component.extend(UppyUploadMixin, {
classNames: ["chat-composer-uploads"],
mediaOptimizationWorker: service(),
chatStateManager: service(),
id: "chat-composer-uploader",
type: "chat-composer",
uploads: null,
useMultipartUploadsIfAvailable: true,
init() {
this._super(...arguments);
this.setProperties({
uploads: [],
fileInputSelector: `#${this.fileUploadElementId}`,
});
this.appEvents.on("chat-composer:load-uploads", this, "_loadUploads");
},
didInsertElement() {
this._super(...arguments);
this.composerInputEl = document.querySelector(".chat-composer-input");
this.composerInputEl?.addEventListener("paste", this._pasteEventListener);
},
willDestroyElement() {
this._super(...arguments);
this.appEvents.off("chat-composer:load-uploads", this, "_loadUploads");
this.composerInputEl?.removeEventListener(
"paste",
this._pasteEventListener
);
},
uploadDone(upload) {
this.uploads.pushObject(upload);
this.onUploadChanged(this.uploads);
},
@discourseComputed("uploads.length", "inProgressUploads.length")
showUploadsContainer(uploadsCount, inProgressUploadsCount) {
return uploadsCount > 0 || inProgressUploadsCount > 0;
},
@action
cancelUploading(upload) {
this.appEvents.trigger(`upload-mixin:${this.id}:cancel-upload`, {
fileId: upload.id,
});
this.uploads.removeObject(upload);
this.onUploadChanged(this.uploads);
},
@action
removeUpload(upload) {
this.uploads.removeObject(upload);
this.onUploadChanged(this.uploads);
},
_uploadDropTargetOptions() {
let targetEl;
if (this.chatStateManager.isFullPageActive) {
targetEl = document.querySelector(".full-page-chat");
} else {
targetEl = document.querySelector(".chat-drawer.is-expanded");
}
if (!targetEl) {
return this._super();
}
return {
target: targetEl,
};
},
_loadUploads(uploads) {
this._uppyInstance?.cancelAll();
this.set("uploads", uploads);
},
_uppyReady() {
if (this.siteSettings.composer_media_optimization_image_enabled) {
this._useUploadPlugin(UppyMediaOptimization, {
optimizeFn: (data, opts) =>
this.mediaOptimizationWorker.optimizeImage(data, opts),
runParallel: !this.site.isMobileDevice,
});
}
this._onPreProcessProgress((file) => {
const inProgressUpload = this.inProgressUploads.findBy("id", file.id);
if (!inProgressUpload?.processing) {
inProgressUpload?.set("processing", true);
}
});
this._onPreProcessComplete((file) => {
const inProgressUpload = this.inProgressUploads.findBy("id", file.id);
inProgressUpload?.set("processing", false);
});
},
@bind
_pasteEventListener(event) {
if (document.activeElement !== this.composerInputEl) {
return;
}
const { canUpload, canPasteHtml, types } = clipboardHelpers(event, {
siteSettings: this.siteSettings,
canUpload: true,
});
if (!canUpload || canPasteHtml || types.includes("text/plain")) {
return;
}
if (event && event.clipboardData && event.clipboardData.files) {
this._addFiles([...event.clipboardData.files], { pasted: true });
}
},
});