58 public function save_upload(
int $rid,
$db, array &$data = array(),
string &$error =
''): bool {
60 if (!$this->has_upload_file(
'upload_file')) {
64 $oUpload =
dbx()->get_system_obj(
'dbxUpload');
65 $oUpload->upload($_FILES[
'upload_file']);
66 $oUpload->allowed = array(
'image/jpeg',
'image/jpg',
'image/pjpeg',
'image/png',
'image/x-png',
'image/webp',
'image/x-webp',
'image/gif');
67 $oUpload->file_max_size = 2 * 1024 * 1024;
68 $oUpload->file_overwrite =
true;
69 $oUpload->file_new_name_body =
'avatar-' . $rid;
70 $oUpload->file_new_name_ext =
'webp';
71 $oUpload->image_convert =
'webp';
72 $oUpload->webp_quality = 86;
73 $oUpload->image_resize =
true;
74 $oUpload->image_ratio_crop =
true;
75 $oUpload->image_x = 640;
76 $oUpload->image_y = 640;
77 $oUpload->process($this->avatar_dir());
79 if ($oUpload->processed) {
80 $ok =
$db->update($this->ddUser, array(
'avatar' => $oUpload->file_dst_name), $rid);
82 $data[
'avatar'] = $oUpload->file_dst_name;
83 $this->remove_old_avatar_files($rid, $oUpload->file_dst_name);
87 $error =
'Profilbild konnte nicht gespeichert werden.';
89 $error =
'Upload fehlgeschlagen: ' . $oUpload->error;
96 public function run() {
97 $uid = (int)
dbx()->user();
101 $db =
dbx()->get_system_obj(
'dbxDB');
102 $data =
$db->select1($this->ddUser, $rid);
103 if (!is_array($data)) {
104 return '<div class="alert alert-warning">Benutzer nicht gefunden.</div>';
107 $oForm = new \dbxForm();
108 $oForm->init(
'dbxUser_avatar',
'form-avatar');
109 $oForm->set_workflow_scope(
'self-' . $uid);
110 $oForm->_data = $data;
111 $oForm->_dd = $this->ddUser;
112 $oForm->_action =
'?dbx_modul=dbxUser&dbx_run1=user&dbx_run2=edit_avatar';
113 $oForm->_msg_info =
'';
115 $oForm->set_state_value(
'rid', $uid);
117 if ($oForm->submit()) {
118 if (!$this->has_upload_file(
'upload_file')) {
119 $oForm->_msg_error =
'Bitte waehlen Sie eine Bilddatei aus.';
123 $oForm->_msg_success = $ok ?
'Avatar gespeichert.' :
'';
124 $oForm->_msg_error = $ok ?
'' : $avatarError;
128 $oForm->add_obj(
'avatar_preview',
'obj-value',
'<img class="dbx-avatar-img" src="' . $this->avatar_url($data[
'avatar'] ??
'') .
'?' . time() .
'" alt="Avatar">');
129 $oForm->add_js_code(<<<
'JS'
131 var drop = document.getElementById(
'uploader_{i}');
132 var panel = document.getElementById(
'dbx_avatar_panel_{i}');
133 if (!drop || !panel || drop.dataset.ready ===
'1')
return;
134 drop.dataset.ready =
'1';
136 var input = panel.querySelector(
'input[type="file"][name="upload_file"]');
137 var title = drop.querySelector(
'.dbx-avatar-drop-title');
138 var meta = drop.querySelector(
'.dbx-avatar-drop-meta');
139 var defaultTitle = title ? title.textContent :
'';
140 var defaultMeta = meta ? meta.textContent :
'';
143 function setBusy(active) {
145 drop.classList.toggle(
'is-active', active);
146 drop.classList.toggle(
'is-uploading', active);
147 drop.setAttribute(
'aria-busy', active ?
'true' :
'false');
148 if (title) title.textContent = active ?
'Upload laeuft...' : (drop.dataset.fileName || defaultTitle);
149 if (meta && active) meta.textContent =
'Datei wurde ausgewaehlt.';
152 function setMessage(message) {
153 if (meta && message) meta.textContent = message;
156 function setSelected(file) {
158 drop.dataset.fileName = file.name || defaultTitle;
159 drop.classList.add(
'has-file');
160 if (title) title.textContent = file.name || defaultTitle;
161 if (meta) meta.textContent =
'Bereit zum Hochladen.';
164 function syncInput(file) {
165 if (!input || !file)
return false;
167 var transfer =
new DataTransfer();
168 transfer.items.add(file);
169 input.files = transfer.files;
170 return input.files && input.files.length === 1;
176 function send(file, fileAlreadyOnInput) {
177 if (!file || busy)
return;
179 fileAlreadyOnInput || syncInput(file);
181 setMessage(
'Profil speichern, um das Bild zu uebernehmen.');
184 function openPicker() {
185 if (!input || busy)
return;
187 if (title) title.textContent = defaultTitle;
188 if (meta) meta.textContent = defaultMeta;
189 drop.classList.remove(
'has-file');
193 drop.addEventListener(
'click',
function () {
194 if (busy)
return false;
196 if (title) title.textContent = defaultTitle;
197 if (meta) meta.textContent = defaultMeta;
198 drop.classList.remove(
'has-file');
200 drop.addEventListener(
'keydown',
function (event) {
201 if (event.key ===
'Enter' || event.key ===
' ') {
202 event.preventDefault();
208 input.addEventListener(
'change',
function () {
209 send(input.files && input.files[0],
true);
213 var outerForm = panel.closest(
'form');
215 outerForm.addEventListener(
'submit',
function () {
216 if (input && input.files && input.files[0]) setBusy(
true);
220 [
'dragenter',
'dragover'].forEach(
function (eventName) {
221 drop.addEventListener(eventName,
function (event) {
222 event.preventDefault();
227 [
'dragleave',
'drop'].forEach(
function (eventName) {
228 drop.addEventListener(eventName,
function (event) {
229 event.preventDefault();
234 drop.addEventListener(
'drop',
function (event) {
235 event.preventDefault();
236 event.stopPropagation();
237 var files =
event.dataTransfer &&
event.dataTransfer.files;
238 send(files && files[0],
false);
243 return $oForm->run();