From 2899cc881b2c9fe24bea4371c1a7f13673ccd6ea Mon Sep 17 00:00:00 2001 From: Sarjuuk Date: Thu, 7 Aug 2025 02:14:46 +0200 Subject: [PATCH] Template/Update (Part 12) * convert user page * update db to handle custom avatars --- endpoints/user/user.php | 359 ++++++++++++++++++++++++++++++++ includes/dbtypes/user.class.php | 17 +- includes/defines.php | 19 +- localization/locale_dede.php | 36 ++-- localization/locale_enus.php | 38 ++-- localization/locale_eses.php | 36 ++-- localization/locale_frfr.php | 36 ++-- localization/locale_ruru.php | 42 ++-- localization/locale_zhcn.php | 42 ++-- pages/user.php | 269 ------------------------ setup/updates/1758578400_04.sql | 17 ++ template/pages/user.tpl.php | 26 ++- 12 files changed, 531 insertions(+), 406 deletions(-) create mode 100644 endpoints/user/user.php delete mode 100644 pages/user.php create mode 100644 setup/updates/1758578400_04.sql diff --git a/endpoints/user/user.php b/endpoints/user/user.php new file mode 100644 index 00000000..7f4fee64 --- /dev/null +++ b/endpoints/user/user.php @@ -0,0 +1,359 @@ +forward('?user='.User::$username); + + if (!$pageParam) + $this->forwardToSignIn('user'); + + if ($user = DB::Aowow()->selectRow('SELECT a.`id`, a.`username`, a.`consecutiveVisits`, a.`userGroups`, a.`avatar`, a.`wowicon`, a.`title`, a.`description`, a.`joinDate`, a.`prevLogin`, IFNULL(SUM(ar.`amount`), 0) AS "sumRep", a.`prevIP`, a.`email` FROM ?_account a LEFT JOIN ?_account_reputation ar ON a.`id` = ar.`userId` WHERE LOWER(a.`username`) = LOWER(?) GROUP BY a.`id`', $pageParam)) + $this->user = $user; + else + $this->generateNotFound(Lang::user('notFound', [$pageParam])); + } + + protected function generate() : void + { + /*********/ + /* Title */ + /*********/ + + array_unshift($this->title, Lang::user('profileTitle', [$this->user['username']])); + + + /***********/ + /* Infobox */ + /***********/ + + $infobox = $contrib = $groups = []; + + foreach (Lang::account('groups') as $idx => $grp) + if ($idx >= 0 && $this->user['userGroups'] & (1 << $idx)) + $groups[] = (!fMod(count($groups) + 1, 3) ? '[br]' : '').$grp; + + if (User::isInGroup(U_GROUP_STAFF)) + { + $infobox[] = Lang::account('lastIP'). $this->user['prevIP']; + $infobox[] = Lang::account('email') . Lang::main('colon') . $this->user['email']; + } + + if ($this->user['joinDate']) + $infobox[] = Lang::user('joinDate') . '[tooltip name=joinDate]'. date('l, G:i:s', $this->user['joinDate']). '[/tooltip][span class=tip tooltip=joinDate]'. date(Lang::main('dateFmtShort'), $this->user['joinDate']). '[/span]'; + if ($this->user['prevLogin']) + $infobox[] = Lang::user('lastLogin') . '[tooltip name=lastLogin]'.date('l, G:i:s', $this->user['prevLogin']).'[/tooltip][span class=tip tooltip=lastLogin]'.date(Lang::main('dateFmtShort'), $this->user['prevLogin']).'[/span]'; + if ($groups) + $infobox[] = Lang::user('userGroups') . implode(', ', $groups); + + $infobox[] = Lang::user('consecVisits'). $this->user['consecutiveVisits']; + $infobox[] = Lang::main('siteRep') . Lang::nf($this->user['sumRep']); + + if ($infobox) + $this->infobox = new InfoboxMarkup($infobox, ['allow' => Markup::CLASS_STAFF], 'infobox-contents0'); + + if ($_ = $this->getCommentStats()) + $contrib[] = $_; + + if ($_ = $this->getScreenshotStats()) + $contrib[] = $_; + + if ($_ = $this->getVideoStats()) + $contrib[] = $_; + + if ($_ = $this->getForumStats()) + $contrib[] = $_; + + // $contrib[] = [url=http://www.wowhead.com/client]Data uploads: n [small]([tooltip=tooltip_totaldatauploads]xx.y MB[/tooltip])[/small][/url] + + if ($contrib) + $this->contributions = new InfoboxMarkup($contrib, ['allow' => Markup::CLASS_STAFF], 'infobox-contents1'); + + + /****************/ + /* Main Content */ + /****************/ + + $this->h1 = $this->user['title'] ? $this->user['username'].' <'.$this->user['title'].'>' : Lang::user('profileTitle', [$this->user['username']]); + + if ($this->user['avatar']) + { + $avatarMore = match ((int)$this->user['avatar']) + { + 1 => $this->user['wowicon'], + 2 => DB::Aowow()->selectCell('SELECT `id` FROM ?_account_avatars WHERE `current` = 1 AND `userId` = ?d', $this->user['id']), + default => '' + }; + + $this->userIcon = array( // JS: Icon.createUser() + $this->user['avatar'], // avatar: 1(iconString), 2(customId) + $avatarMore, // avatarMore: iconString or customId + IconElement::SIZE_MEDIUM, // size: (always medium) + null, // url: (always null) + User::isInGroup(U_GROUP_PREMIUM) ? 0 : 2, // premiumLevel: affixes css class ['-premium', '-gold', '', '-premiumred', '-red'] + false, // noBorder: always false + '$Icon.getPrivilegeBorder('.$this->user['sumRep'].')' // reputationLevel: calculated in js from passed rep points + ); + } + + $this->username = $this->user['username']; + + if ($this->user['description']) // seen CLASS_STAFF, but wouldn't dare.. filtered for restricted tags before sent? + $this->description = new Markup($this->user['description'], ['allow' => ($this->user['userGroups'] & U_GROUP_PREMIUM) ? Markup::CLASS_PREMIUM : Markup::CLASS_USER], 'description-generic'); + + + /**************/ + /* Extra Tabs */ + /**************/ + + $this->lvTabs = new Tabs(['parent' => "\$\$WH.ge('tabs-generic')"], 'tabsRelated', true); + + // [unused] Site Achievements + + // Reputation changelog (params only for comment-events) + if (User::$id == $this->user['id'] || User::isInGroup(U_GROUP_MODERATOR)) + if ($repData = DB::Aowow()->select('SELECT `action`, `amount`, `date` AS "when", IF(`action` IN (3, 4, 5), `sourceA`, 0) AS "param" FROM ?_account_reputation WHERE `userId` = ?d', $this->user['id'])) + { + array_walk($repData, fn(&$x) => $x['when'] = date(Util::$dateFormatInternal, $x['when'])); + $this->lvTabs->addListviewTab(new Listview(['data' => $repData], 'reputationhistory')); + } + + // Comments + if ($_ = CommunityContent::getCommentPreviews(['user' => $this->user['id'], 'comments' => true], $nFound)) + { + $tabData = array( + 'data' => $_, + 'hiddenCols' => ['author'], + 'onBeforeCreate' => '$Listview.funcBox.beforeUserComments', + '_totalCount' => $nFound + ); + + if ($nFound > Cfg::get('SQL_LIMIT_DEFAULT')) + { + $tabData['name'] = '$LANG.tab_latestcomments'; + $tabData['note'] = '$$WH.sprintf(LANG.lvnote_usercomments, '.$nFound.')'; + } + + $this->lvTabs->addListviewTab(new Listview($tabData, 'commentpreview')); + } + + // Comment Replies + if ($_ = CommunityContent::getCommentPreviews(['user' => $this->user['id'], 'replies' => true], $nFound)) + { + $tabData = array( + 'data' => $_, + 'hiddenCols' => ['author'], + 'onBeforeCreate' => '$Listview.funcBox.beforeUserComments', + '_totalCount' => $nFound + ); + + if ($nFound > Cfg::get('SQL_LIMIT_DEFAULT')) + { + $tabData['name'] = '$LANG.tab_latestreplies'; + $tabData['note'] = '$$WH.sprintf(LANG.lvnote_userreplies, '.$nFound.')'; + } + + $this->lvTabs->addListviewTab(new Listview($tabData, 'replypreview')); + } + + // Screenshots + if ($_ = CommunityContent::getScreenshots(-$this->user['id'], 0, $nFound)) + { + $tabData = array( + 'data' => $_, + '_totalCount' => $nFound + ); + + if ($nFound > Cfg::get('SQL_LIMIT_DEFAULT')) + { + $tabData['name'] = '$LANG.tab_latestscreenshots'; + $tabData['note'] = '$$WH.sprintf(LANG.lvnote_userscreenshots, '.$nFound.')'; + } + + $this->lvTabs->addListviewTab(new Listview($tabData, 'screenshot')); + } + + // Videos + if ($_ = CommunityContent::getVideos(-$this->user['id'], 0, $nFound)) + { + $tabData = array( + 'data' => $_, + '_totalCount' => $nFound + ); + + if ($nFound > Cfg::get('SQL_LIMIT_DEFAULT')) + { + $tabData['name'] = '$LANG.tab_latestvideos'; + $tabData['note'] = '$$WH.sprintf(LANG.lvnote_uservideos, '.$nFound.')'; + } + + $this->lvTabs->addListviewTab(new Listview($tabData, 'video')); + } + + // forum -> latest topics [unused] + + // forum -> latest replies [unused] + + if (Cfg::get('PROFILER_ENABLE')) + { + $conditions = array( + ['OR', ['cuFlags', PROFILER_CU_PUBLISHED, '&'], ['ap.extraFlags', PROFILER_CU_PUBLISHED, '&']], + [['cuFlags', PROFILER_CU_DELETED, '&'], 0], + ['OR', ['user', $this->user['id']], ['ap.accountId', $this->user['id']]] + ); + + if (User::isInGroup(U_GROUP_ADMIN | U_GROUP_BUREAU)) + $conditions = array_slice($conditions, 2); + else if (User::$id == $this->user['id']) + array_shift($conditions); + + $profiles = new LocalProfileList($conditions); + if (!$profiles->error) + { + $this->addDataLoader('weight-presets'); + + // Characters + if ($chars = $profiles->getListviewData(PROFILEINFO_CHARACTER | PROFILEINFO_USER)) + $this->charactersLvData = array_values($chars); + + // Profiles + if ($prof = $profiles->getListviewData(PROFILEINFO_PROFILE | PROFILEINFO_USER)) + $this->profilesLvData = array_values($prof); + } + } + + // My Guides + $guides = new GuideList(['status', [GUIDE_STATUS_APPROVED, GUIDE_STATUS_ARCHIVED]], ['userId', $this->user['id']]); + if (!$guides->error) + { + $this->lvTabs->addListviewTab(new Listview(array( + 'data' => $guides->getListviewData(), + 'hiddenCols' => ['patch'] + ), GuideList::$brickFile)); + } + + parent::generate(); + } + + private function getCommentStats() : ?string + { + $co = DB::Aowow()->selectRow( + 'SELECT COUNT(DISTINCT c.`id`) AS "0", SUM(IFNULL(ur.`value`, 0)) AS "1" FROM ?_comments c LEFT JOIN ?_user_ratings ur ON ur.`entry` = c.`id` AND ur.`type` = ?d AND ur.`userId` <> 0 WHERE c.`replyTo` = 0 AND c.`userId` = ?d', + RATING_COMMENT, $this->user['id'] + ); + + if (!$co) + return null; + + [$sum, $nRatings] = $co; + + return Lang::user('comments').$sum.($nRatings ? ' [small]([tooltip=tooltip_totalratings]'.$nRatings.'[/tooltip])[/small]' : ''); + } + + private function getScreenshotStats() : ?string + { + $ss = DB::Aowow()->selectRow( + 'SELECT COUNT(*) AS "0", SUM(IF(`status` & ?d, 1, 0)) AS "1", SUM(IF(`status` & ?d, 0, 1)) AS "2" FROM ?_screenshots WHERE `userIdOwner` = ?d AND (`status` & ?d) = 0', + CC_FLAG_STICKY, CC_FLAG_APPROVED, $this->user['id'], CC_FLAG_DELETED + ); + + if (!$ss) + return null; + + [$sum, $nSticky, $nPending] = $ss; + + $buff = []; + if ($nSticky || $nPending) + { + if ($normal = ($sum - $nSticky - $nPending)) + $buff[] = '[tooltip=tooltip_normal]'.$normal.'[/tooltip]'; + + if ($nSticky) + $buff[] = '[tooltip=tooltip_sticky]'.$nSticky.'[/tooltip]'; + + if ($nPending) + $buff[] = '[tooltip=tooltip_pending]'.$nPending.'[/tooltip]'; + } + + return Lang::user('screenshots').$sum.($buff ? ' [small]('.implode(' + ', $buff).')[/small]' : ''); + } + + private function getVideoStats() : ?string + { + $vi = DB::Aowow()->selectRow( + 'SELECT COUNT(*) AS "0", SUM(IF(`status` & ?d, 1, 0)) AS "1", SUM(IF(`status` & ?d, 0, 1)) AS "2" FROM ?_videos WHERE `userIdOwner` = ?d AND (`status` & ?d) = 0', + CC_FLAG_STICKY, CC_FLAG_APPROVED, $this->user['id'], CC_FLAG_DELETED + ); + + if (!$vi) + return null; + + [$sum, $nSticky, $nPending] = $vi; + + $buff = []; + if ($nSticky || $nPending) + { + if ($normal = ($sum - $nSticky - $nPending)) + $buff[] = '[tooltip=tooltip_normal]'.$normal.'[/tooltip]'; + + if ($nSticky) + $buff[] = '[tooltip=tooltip_sticky]'.$nSticky.'[/tooltip]'; + + if ($nPending) + $buff[] = '[tooltip=tooltip_pending]'.$nPending.'[/tooltip]'; + } + + return Lang::user('videos').$sum.($buff ? ' [small]('.implode(' + ', $buff).')[/small]' : ''); + } + + private function getForumStats() : ?string + { + $fo = null; // some query + + if (!$fo) + return null; + + [$nTopics, $nReplies] = $fo; + + $buff = []; + if ($nTopics) + $buff[] = '[tooltip=topics]'.$nTopics.'[/tooltip]'; + + if ($nReplies) + $buff[] = '[tooltip=replies]'.$nReplies.'[/tooltip]'; + + return Lang::user('posts').($nTopics + $nReplies).($buff ? ' [small]('.implode(' + ', $buff).')[/small]' : ''); + } +} + +?> diff --git a/includes/dbtypes/user.class.php b/includes/dbtypes/user.class.php index 59d346ef..1d356760 100644 --- a/includes/dbtypes/user.class.php +++ b/includes/dbtypes/user.class.php @@ -23,7 +23,7 @@ class UserList extends DBTypeList { $data = []; - foreach ($this->iterate() as $__) + foreach ($this->iterate() as $userId => $__) { $data[$this->curTpl['username']] = array( 'border' => 0, // border around avatar (rarityColors) @@ -40,10 +40,19 @@ class UserList extends DBTypeList if ($_ = $this->curTpl['title']) $data[$this->curTpl['username']]['title'] = $_; - if ($_ = $this->curTpl['avatar']) + switch ($this->curTpl['avatar']) { - $data[$this->curTpl['username']]['avatar'] = is_numeric($_) ? 2 : 1; - $data[$this->curTpl['username']]['avatarmore'] = $_; + case 1: + $data[$this->curTpl['username']]['avatar'] = $this->curTpl['avatar']; + $data[$this->curTpl['username']]['avatarmore'] = $this->curTpl['wowicon']; + break; + case 2: + if ($av = DB::Aowow()->selectCell('SELECT `id` FROM ?_account_avatars WHERE `userId` = ?d AND `current` = 1 AND `status` <> 2', $userId)) + { + $data[$this->curTpl['username']]['avatar'] = $this->curTpl['avatar']; + $data[$this->curTpl['username']]['avatarmore'] = $av; + } + break; } // more optional data diff --git a/includes/defines.php b/includes/defines.php index 194f70e5..b50eee78 100644 --- a/includes/defines.php +++ b/includes/defines.php @@ -73,15 +73,16 @@ define('SESSION_LOGOUT', 2); define('SESSION_FORCED_LOGOUT', 3); define('SESSION_EXPIRED', 4); -define('ACC_BAN_NONE', 0x00); // all clear -define('ACC_BAN_TEMP', 0x01); -define('ACC_BAN_PERM', 0x02); -define('ACC_BAN_RATE', 0x04); // cannot rate community items (overrides site reputation) -define('ACC_BAN_COMMENT', 0x08); // cannot comment and reply -define('ACC_BAN_UPLOAD', 0x10); // cannot upload avatar / signature files [originally: ban from data upload] -define('ACC_BAN_SCREENSHOT', 0x20); // cannot upload screenshots -define('ACC_BAN_VIDEO', 0x40); // cannot suggest videos -define('ACC_BAN_GUIDE', 0x80); // cannot write a guide +define('ACC_BAN_NONE', 0x0000); // all clear +define('ACC_BAN_TEMP', 0x0001); +define('ACC_BAN_PERM', 0x0002); +define('ACC_BAN_RATE', 0x0004); // cannot rate community items (overrides site reputation) +define('ACC_BAN_COMMENT', 0x0008); // cannot comment and reply +define('ACC_BAN_UPLOAD', 0x0010); // cannot upload avatar / signature files [originally: ban from data upload] +define('ACC_BAN_SCREENSHOT', 0x0020); // cannot upload screenshots +define('ACC_BAN_VIDEO', 0x0040); // cannot suggest videos +define('ACC_BAN_GUIDE', 0x0080); // cannot write a guide +define('ACC_BAN_FORUM', 0x0100); // cannot post on forums [not used here] // Site Reputation/Privileges define('SITEREP_ACTION_REGISTER', 1); // Registered account diff --git a/localization/locale_dede.php b/localization/locale_dede.php index 958b3d1f..5bf20b79 100644 --- a/localization/locale_dede.php +++ b/localization/locale_dede.php @@ -47,7 +47,7 @@ $lang = array( 'gains' => "Belohnungen", 'login' => "Login", 'forum' => "Forum", - 'siteRep' => "Ruf", + 'siteRep' => "Ruf: ", 'yourRepHistory'=> "Dein Ruf-Verlauf", 'aboutUs' => "Über Aowow", 'and' => " und ", @@ -908,18 +908,18 @@ $lang = array( 'passConfirm' => "Kennwort bestätigen", // dashboard - 'ipAddress' => "IP-Adresse", - 'lastIP' => "Letzte bekannte IP", - 'myAccount' => "Mein Account", - 'editAccount' => "Benutze die folgenden Formulare um deine Account-Informationen zu aktualisieren", - 'viewPubDesc' => 'Die Beschreibung in deinem öffentlichen Profil ansehen', + 'ipAddress' => "IP-Adresse: ", + 'lastIP' => "Letzte bekannte IP: ", + // 'myAccount' => "Mein Account", + // 'editAccount' => "Benutze die folgenden Formulare um deine Account-Informationen zu aktualisieren", + // 'viewPubDesc' => 'Die Beschreibung in deinem öffentlichen Profil ansehen', // bans 'accBanned' => "Dieses Konto wurde geschlossen", - 'bannedBy' => "Gebannt durch", - 'ends' => "Endet am", + 'bannedBy' => "Gebannt durch: ", + 'reason' => "Grund: ", + 'ends' => "Endet am: ", 'permanent' => "Der Bann ist permanent", - 'reason' => "Grund", 'noReason' => "Es wurde kein Grund angegeben.", // form-text @@ -947,18 +947,18 @@ $lang = array( 'user' => array( 'notFound' => "Der Benutzer \"%s\" wurde nicht gefunden!", 'removed' => "(Entfernt)", - 'joinDate' => "Mitglied seit", - 'lastLogin' => "Letzter Besuch", - 'userGroups' => "Rolle", - 'consecVisits' => "Aufeinanderfolgende Besuche", + 'joinDate' => "Mitglied seit: ", + 'lastLogin' => "Letzter Besuch: ", + 'userGroups' => "Rolle: ", + 'consecVisits' => "Aufeinanderfolgende Besuche: ", 'publicDesc' => "Öffentliche Beschreibung", 'profileTitle' => "Profil von %s", 'contributions' => "Beiträge", - 'uploads' => "Hochladevorgänge", - 'comments' => "Kommentare", - 'screenshots' => "Screenshots", - 'videos' => "Videos", - 'posts' => "Forenbeiträge" + 'uploads' => "Hochladevorgänge: ", + 'comments' => "Kommentare: ", + 'screenshots' => "Screenshots: ", + 'videos' => "Videos: ", + 'posts' => "Forenbeiträge: " ), 'emote' => array( 'notFound' => "Dieses Emote existiert nicht.", diff --git a/localization/locale_enus.php b/localization/locale_enus.php index 2d0d0b9e..4ee8b007 100644 --- a/localization/locale_enus.php +++ b/localization/locale_enus.php @@ -47,7 +47,7 @@ $lang = array( 'gains' => "Gains", 'login' => "Login", 'forum' => "Forum", - 'siteRep' => "Reputation", + 'siteRep' => "Reputation: ", 'yourRepHistory'=> "Your Reputation History", 'aboutUs' => "About us & contact", 'and' => " and ", @@ -908,18 +908,18 @@ $lang = array( 'passConfirm' => "Confirm password", // dashboard - 'ipAddress' => "IP address", - 'lastIP' => "last used IP", - 'myAccount' => "My Account", - 'editAccount' => "Simply use the forms below to update your account information", - 'viewPubDesc' => 'View your Public Description in your Profile Page', + 'ipAddress' => "IP address: ", + 'lastIP' => "last used IP: ", + // 'myAccount' => "My Account", + // 'editAccount' => "Simply use the forms below to update your account information", + // 'viewPubDesc' => 'View your Public Description in your Profile Page', // bans - 'accBanned' => "This Account was closed", - 'bannedBy' => "Banned by", - 'ends' => "Ends on", + 'accBanned' => "This account was closed", + 'bannedBy' => "Banned by: ", + 'reason' => "Reason: ", + 'ends' => "Ends on: ", 'permanent' => "The ban is permanent", - 'reason' => "Reason", 'noReason' => "No reason was given.", // form-text @@ -947,18 +947,18 @@ $lang = array( 'user' => array( 'notFound' => "User \"%s\" not found!", 'removed' => "(Removed)", - 'joinDate' => "Joined", - 'lastLogin' => "Last visit", - 'userGroups' => "Role", - 'consecVisits' => "Consecutive visits", + 'joinDate' => "Joined: ", + 'lastLogin' => "Last visit: ", + 'userGroups' => "Role: ", + 'consecVisits' => "Consecutive visits: ", 'publicDesc' => "Public Description", 'profileTitle' => "%s's Profile", 'contributions' => "Contributions", - 'uploads' => "Data uploads", - 'comments' => "Comments", - 'screenshots' => "Screenshots", - 'videos' => "Videos", - 'posts' => "Forum posts" + 'uploads' => "Data uploads: ", + 'comments' => "Comments: ", + 'screenshots' => "Screenshots: ", + 'videos' => "Videos: ", + 'posts' => "Forum posts: " ), 'emote' => array( 'notFound' => "This Emote doesn't exist.", diff --git a/localization/locale_eses.php b/localization/locale_eses.php index fa17ca26..990a72e8 100644 --- a/localization/locale_eses.php +++ b/localization/locale_eses.php @@ -47,7 +47,7 @@ $lang = array( 'gains' => "Ganancias", 'login' => "Ingresar", 'forum' => "Foro", - 'siteRep' => "Reputación", + 'siteRep' => "Reputación: ", 'yourRepHistory'=> "Tu Historial de Reputación", 'aboutUs' => "Sobre Aowow", 'and' => " y ", @@ -908,18 +908,18 @@ $lang = array( 'passConfirm' => "Confirmar contraseña", // dashboard - 'ipAddress' => "Dirección IP", - 'lastIP' => "Última IP usada", - 'myAccount' => "Mi cuenta", - 'editAccount' => "Use el formulario siguienta para actualizar la información de la cuenta.", - 'viewPubDesc' => 'Mira tu descripción pública en tu Página de perfil', + 'ipAddress' => "Dirección IP: ", + 'lastIP' => "Última IP usada: ", + // 'myAccount' => "Mi cuenta", + // 'editAccount' => "Use el formulario siguienta para actualizar la información de la cuenta.", + // 'viewPubDesc' => 'Mira tu descripción pública en tu Página de perfil', // bans 'accBanned' => "Esta cuenta fue cerrada.", - 'bannedBy' => "Suspendida por", - 'ends' => "Finaliza en", + 'bannedBy' => "Suspendida por: ", + 'reason' => "Razón: ", + 'ends' => "Finaliza en: ", 'permanent' => "La restricción es permanente", - 'reason' => "Razón", 'noReason' => "Ningúna razón fue escrita.", // form-text @@ -947,18 +947,18 @@ $lang = array( 'user' => array( 'notFound' => "¡No se encontró el usuario \"%s\"!", 'removed' => "(Removido)", - 'joinDate' => "Se unió", - 'lastLogin' => "Última visita", - 'userGroups' => "Rol", - 'consecVisits' => "Visitas consecutivas", + 'joinDate' => "Se unió: ", + 'lastLogin' => "Última visita: ", + 'userGroups' => "Rol: ", + 'consecVisits' => "Visitas consecutivas: ", 'publicDesc' => "Descripción pública", 'profileTitle' => "Perfíl de %s", 'contributions' => "Contribuciones", - 'uploads' => "Datos enviados", - 'comments' => "Comentarios", - 'screenshots' => "Capturas de pantalla", - 'videos' => "Vídeos", - 'posts' => "Mensajes en los foros" + 'uploads' => "Datos enviados: ", + 'comments' => "Comentarios: ", + 'screenshots' => "Capturas de pantalla: ", + 'videos' => "Vídeos: ", + 'posts' => "Mensajes en los foros: " ), 'emote' => array( 'notFound' => "Este emoticón no existe.", diff --git a/localization/locale_frfr.php b/localization/locale_frfr.php index 49e972ae..9ec26785 100644 --- a/localization/locale_frfr.php +++ b/localization/locale_frfr.php @@ -47,7 +47,7 @@ $lang = array( 'gains' => "Gains", 'login' => "[Login]", 'forum' => "Forum", - 'siteRep' => "Réputation", + 'siteRep' => "Réputation : ", 'yourRepHistory'=> "Votre historique de réputation", 'aboutUs' => "À propos de Aowow", 'and' => " et ", @@ -908,18 +908,18 @@ $lang = array( 'passConfirm' => "Confirmez", // dashboard - 'ipAddress' => "Addresse IP", - 'lastIP' => "Dernière IP utilisée", - 'myAccount' => "Mon compte", - 'editAccount' => "Utilisez les formulaires ci-dessous pour mettre à jour vos informations.", - 'viewPubDesc' => 'Voyez vos informations publiques dans votre Profile Page', + 'ipAddress' => "Addresse IP : ", + 'lastIP' => "Dernière IP utilisée : ", + // 'myAccount' => "Mon compte", + // 'editAccount' => "Utilisez les formulaires ci-dessous pour mettre à jour vos informations.", + // 'viewPubDesc' => 'Voyez vos informations publiques dans votre Profile Page', // bans 'accBanned' => "Ce compte a été fermé.", - 'bannedBy' => "Banni par", - 'ends' => "Termine le", + 'bannedBy' => "Banni par : ", + 'reason' => "Raison : ", + 'ends' => "Termine le : ", 'permanent' => "Ce bannissement est permanent", - 'reason' => "Raison", 'noReason' => "Aucune raison donnée.", // form-text @@ -947,18 +947,18 @@ $lang = array( 'user' => array( 'notFound' => "Utilisateur \"%s\" non trouvé!", 'removed' => "(Supprimé)", - 'joinDate' => "Inscription", - 'lastLogin' => "Dernière visite", - 'userGroups' => "Role", - 'consecVisits' => "Visites consécutives", + 'joinDate' => "Inscription : ", + 'lastLogin' => "Dernière visite : ", + 'userGroups' => "Role : ", + 'consecVisits' => "Visites consécutives : ", 'publicDesc' => "Description publique", 'profileTitle' => "Profil de %s", 'contributions' => "Contributions", - 'uploads' => "Envois de données", - 'comments' => "Commentaires", - 'screenshots' => "Captures d'écran", - 'videos' => "Vidéos", - 'posts' => "Messages sur le forum" + 'uploads' => "Envois de données : ", + 'comments' => "Commentaires : ", + 'screenshots' => "Captures d'écran : ", + 'videos' => "Vidéos : ", + 'posts' => "Messages sur le forum : " ), 'emote' => array( 'notFound' => "[This Emote doesn't exist.]", diff --git a/localization/locale_ruru.php b/localization/locale_ruru.php index 888096ff..eb19d8c7 100644 --- a/localization/locale_ruru.php +++ b/localization/locale_ruru.php @@ -47,7 +47,7 @@ $lang = array( 'gains' => "Бонус", 'login' => "[Login]", 'forum' => "Форум", - 'siteRep' => "Репутация", + 'siteRep' => "Репутация: ", 'yourRepHistory'=> "История вашей репутации", 'aboutUs' => "О Aowow", 'and' => " и ", @@ -908,19 +908,19 @@ $lang = array( 'passConfirm' => "Повторите пароль", // dashboard - 'ipAddress' => "IP-Adress", - 'lastIP' => "last used IP", - 'myAccount' => "My Account", - 'editAccount' => "Simply use the forms below to update your account information", - 'viewPubDesc' => 'View your Public Description in your Profile Page', + 'ipAddress' => "[IP-Adress]: ", + 'lastIP' => "[last used IP]: ", + // 'myAccount' => "[My Account]", + // 'editAccount' => "[Simply use the forms below to update your account information]", + // 'viewPubDesc' => '[View your Public Description in your Profile Page]', // bans - 'accBanned' => "This Account was closed", - 'bannedBy' => "Banned by", - 'ends' => "Ends on", - 'permanent' => "The ban is permanent", - 'reason' => "Reason", - 'noReason' => "No reason was given.", + 'accBanned' => "[This Account was closed]", + 'bannedBy' => "[Banned by]: ", + 'reason' => "[Reason]: ", + 'ends' => "[Ends on]: ", + 'permanent' => "[The ban is permanent]", + 'noReason' => "[No reason was given.]", // form-text 'emailInvalid' => "Недопустимый адрес email.", // message_emailnotvalid @@ -947,18 +947,18 @@ $lang = array( 'user' => array( 'notFound' => "Пользователь \"%s\" не найден!", 'removed' => "(Удалено)", - 'joinDate' => "Зарегистрировался", - 'lastLogin' => "Последняя активность", - 'userGroups' => "Роль", - 'consecVisits' => "Регулярные посещения", + 'joinDate' => "Зарегистрировался:", + 'lastLogin' => "Последняя активность:", + 'userGroups' => "Роль:", + 'consecVisits' => "Регулярные посещения:", 'publicDesc' => "Описание", 'profileTitle' => "Профиль %s", 'contributions' => "Вклад", - 'uploads' => "Данных загружено", - 'comments' => "Комментарии", - 'screenshots' => "Скриншоты", - 'videos' => "Видео", - 'posts' => "Сообщений на форумах" + 'uploads' => "Данных загружено: ", + 'comments' => "Комментарии: ", + 'screenshots' => "Скриншоты: ", + 'videos' => "Видео: ", + 'posts' => "Сообщений на форумах: " ), 'emote' => array( 'notFound' => "[This Emote doesn't exist.]", diff --git a/localization/locale_zhcn.php b/localization/locale_zhcn.php index 78690188..eee9b77b 100644 --- a/localization/locale_zhcn.php +++ b/localization/locale_zhcn.php @@ -48,7 +48,7 @@ $lang = array( 'gains' => "获得", 'login' => "登录", 'forum' => "论坛", - 'siteRep' => "站点声望", + 'siteRep' => "站点声望:", 'yourRepHistory'=> "您的声望历史", 'aboutUs' => "关于我们 & 联系我们", 'and' => "和", @@ -71,7 +71,7 @@ $lang = array( 'oneFilter' => "至少一个", 'applyFilter' => "应用过滤", 'resetForm' => "清除表单", - 'refineSearch' => '提示: 通过浏览 子类别搜索。', + 'refineSearch' => '提示:通过浏览 子类别搜索。', 'clear' => "清除", 'exactMatch' => "精确匹配", '_reqLevel' => "要求等级", @@ -111,7 +111,7 @@ $lang = array( 'addWeight' => "添加另一个权重", 'createWS' => "创建一个权重比例", 'jcGemsOnly' => "包含JC-only宝石", - 'cappedHint' => '提示: 移除 命中等级等上限属性的权重。', + 'cappedHint' => '提示:移除 命中等级等上限属性的权重。', 'groupBy' => "按组", 'gb' => array( ["无", "none"], ["插槽", "slot"], ["等级", "level"], ["来源", "source"] @@ -270,7 +270,7 @@ $lang = array( 'thanks' => array( 'contrib' => "非常感谢你的贡献!", 'goBack' => '点击这里返回上一页。', - 'note' => "注意: 你的截图显示在网站前需要审核。这需要最多72小时。" + 'note' => "注意:你的截图显示在网站前需要审核。这需要最多72小时。" ), 'error' => array( 'unkFormat' => "未知图像格式。", @@ -908,18 +908,18 @@ $lang = array( 'passConfirm' => "确认密码", // dashboard - 'ipAddress' => "IP地址", - 'lastIP' => "上次使用IP地址", - 'myAccount' => "我的账号", - 'editAccount' => "只需使用以下表格就能更新你的帐户信息", - 'viewPubDesc' => '在你的简介页面查看你公共描述', + 'ipAddress' => "IP地址:", + 'lastIP' => "上次使用IP地址:", + // 'myAccount' => "我的账号", + // 'editAccount' => "只需使用以下表格就能更新你的帐户信息", + // 'viewPubDesc' => '在你的简介页面查看你公共描述', // bans 'accBanned' => "这个账号已被关闭", - 'bannedBy' => "冻结操作者", - 'ends' => "结束于", + 'bannedBy' => "冻结操作者:", + 'reason' => "理由:", + 'ends' => "结束于:", 'permanent' => "永久冻结", - 'reason' => "理由", 'noReason' => "没有理由提供。", // form-text @@ -947,18 +947,18 @@ $lang = array( 'user' => array( 'notFound' => "用户 \"%s\" 未找到", 'removed' => "(已移除)", - 'joinDate' => "加入", - 'lastLogin' => "上次访问", - 'userGroups' => "角色", - 'consecVisits' => "连续访问", + 'joinDate' => "加入:", + 'lastLogin' => "上次访问:", + 'userGroups' => "角色:", + 'consecVisits' => "连续访问:", 'publicDesc' => "公共描述", 'profileTitle' => "%s的简介", 'contributions' => "贡献", - 'uploads' => "数据上传", - 'comments' => "评论", - 'screenshots' => "截图", - 'videos' => "视频", - 'posts' => "论坛帖子" + 'uploads' => "数据上传:", + 'comments' => "评论:", + 'screenshots' => "截图:", + 'videos' => "视频:", + 'posts' => "论坛帖子:" ), 'emote' => array( 'notFound' => "这个表情不存在。", diff --git a/pages/user.php b/pages/user.php deleted file mode 100644 index 78323e08..00000000 --- a/pages/user.php +++ /dev/null @@ -1,269 +0,0 @@ -selectRow('SELECT a.`id`, a.`username`, a.`consecutiveVisits`, a.`userGroups`, a.`avatar`, a.`title`, a.`description`, a.`joinDate`, a.`prevLogin`, IFNULL(SUM(ar.`amount`), 0) AS "sumRep" FROM ?_account a LEFT JOIN ?_account_reputation ar ON a.`id` = ar.`userId` WHERE LOWER(a.`username`) = LOWER(?) GROUP BY a.`id`', $pageParam)) - $this->user = $user; - else - $this->notFound(sprintf(Lang::user('notFound'), $pageParam)); - } - else if (User::isLoggedIn()) - { - header('Location: ?user='.User::$username, true, 302); - die(); - } - else - $this->forwardToSignIn('user'); - } - - protected function generateContent() - { - if (!$this->user) // shouldn't happen .. but did - return; - - - /***********/ - /* Infobox */ - /***********/ - - $infobox = $contrib = $groups = []; - foreach (Lang::account('groups') as $idx => $key) - if ($idx >= 0 && $this->user['userGroups'] & (1 << $idx)) - $groups[] = (!fMod(count($groups) + 1, 3) ? '[br]' : null).Lang::account('groups', $idx); - - $infobox[] = Lang::user('joinDate'). Lang::main('colon').'[tooltip name=joinDate]'. date('l, G:i:s', $this->user['joinDate']). '[/tooltip][span class=tip tooltip=joinDate]'. date(Lang::main('dateFmtShort'), $this->user['joinDate']). '[/span]'; - $infobox[] = Lang::user('lastLogin').Lang::main('colon').'[tooltip name=lastLogin]'.date('l, G:i:s', $this->user['prevLogin']).'[/tooltip][span class=tip tooltip=lastLogin]'.date(Lang::main('dateFmtShort'), $this->user['prevLogin']).'[/span]'; - $infobox[] = Lang::user('userGroups').Lang::main('colon').($groups ? implode(', ', $groups) : Lang::account('groups', -1)); - $infobox[] = Lang::user('consecVisits').Lang::main('colon').$this->user['consecutiveVisits']; - $infobox[] = Util::ucFirst(Lang::main('siteRep')).Lang::main('colon').Lang::nf($this->user['sumRep']); - - // contrib -> [url=http://www.wowhead.com/client]Data uploads: n [small]([tooltip=tooltip_totaldatauploads]xx.y MB[/tooltip])[/small][/url] - - $co = DB::Aowow()->selectRow( - 'SELECT COUNT(DISTINCT c.id) AS sum, SUM(IFNULL(ur.value, 0)) AS nRates FROM ?_comments c LEFT JOIN ?_user_ratings ur ON ur.entry = c.id AND ur.type = ?d AND ur.userId <> 0 WHERE c.replyTo = 0 AND c.userId = ?d', - RATING_COMMENT, - $this->user['id'] - ); - if ($co['sum']) - $contrib[] = Lang::user('comments').Lang::main('colon').$co['sum'].($co['nRates'] ? ' [small]([tooltip=tooltip_totalratings]'.$co['nRates'].'[/tooltip])[/small]' : null); - - $ss = DB::Aowow()->selectRow('SELECT COUNT(*) AS sum, SUM(IF(status & ?d, 1, 0)) AS nSticky, SUM(IF(status & ?d, 0, 1)) AS nPending FROM ?_screenshots WHERE userIdOwner = ?d AND (status & ?d) = 0', - CC_FLAG_STICKY, - CC_FLAG_APPROVED, - $this->user['id'], - CC_FLAG_DELETED - ); - if ($ss['sum']) - { - $buff = []; - if ($ss['nSticky'] || $ss['nPending']) - { - if ($normal = ($ss['sum'] - $ss['nSticky'] - $ss['nPending'])) - $buff[] = '[tooltip=tooltip_normal]'.$normal.'[/tooltip]'; - - if ($ss['nSticky']) - $buff[] = '[tooltip=tooltip_sticky]'.$ss['nSticky'].'[/tooltip]'; - - if ($ss['nPending']) - $buff[] = '[tooltip=tooltip_pending]'.$ss['nPending'].'[/tooltip]'; - } - - $contrib[] = Lang::user('screenshots').Lang::main('colon').$ss['sum'].($buff ? ' [small]('.implode(' + ', $buff).')[/small]' : null); - } - - $vi = DB::Aowow()->selectRow('SELECT COUNT(id) AS sum, SUM(IF(status & ?d, 1, 0)) AS nSticky, SUM(IF(status & ?d, 0, 1)) AS nPending FROM ?_videos WHERE userIdOwner = ?d AND (status & ?d) = 0', - CC_FLAG_STICKY, - CC_FLAG_APPROVED, - $this->user['id'], - CC_FLAG_DELETED - ); - if ($vi['sum']) - { - $buff = []; - if ($vi['nSticky'] || $vi['nPending']) - { - if ($normal = ($vi['sum'] - $vi['nSticky'] - $vi['nPending'])) - $buff[] = '[tooltip=tooltip_normal]'.$normal.'[/tooltip]'; - - if ($vi['nSticky']) - $buff[] = '[tooltip=tooltip_sticky]'.$vi['nSticky'].'[/tooltip]'; - - if ($vi['nPending']) - $buff[] = '[tooltip=tooltip_pending]'.$vi['nPending'].'[/tooltip]'; - } - - $contrib[] = Lang::user('videos').Lang::main('colon').$vi['sum'].($buff ? ' [small]('.implode(' + ', $buff).')[/small]' : null); - } - - // contrib -> Forum posts: 5769 [small]([tooltip=topics]579[/tooltip] + [tooltip=replies]5190[/tooltip])[/small] - - $this->infobox = '[ul][li]'.implode('[/li][li]', $infobox).'[/li][/ul]'; - - if ($contrib) - $this->contributions = '[ul][li]'.implode('[/li][li]', $contrib).'[/li][/ul]'; - - - /****************/ - /* Main Content */ - /****************/ - - $this->name = $this->user['title'] ? $this->user['username'].' <'.$this->user['title'].'>' : Lang::user('profileTitle', [$this->user['username']]); - - /**************/ - /* Extra Tabs */ - /**************/ - - // [unused] Site Achievements - - // Reputation changelog (params only for comment-events) - if ($repData = DB::Aowow()->select('SELECT action, amount, date AS \'when\', IF(action IN (3, 4, 5), sourceA, 0) AS param FROM ?_account_reputation WHERE userId = ?d', $this->user['id'])) - { - foreach ($repData as &$r) - $r['when'] = date(Util::$dateFormatInternal, $r['when']); - - $this->lvTabs[] = ['reputationhistory', ['data' => $repData]]; - } - - // Comments - if ($_ = CommunityContent::getCommentPreviews(['user' => $this->user['id'], 'comments' => true], $nFound)) - { - $tabData = array( - 'data' => $_, - 'hiddenCols' => ['author'], - 'onBeforeCreate' => '$Listview.funcBox.beforeUserComments', - '_totalCount' => $nFound - ); - - if ($nFound > Cfg::get('SQL_LIMIT_DEFAULT')) - { - $tabData['name'] = '$LANG.tab_latestcomments'; - $tabData['note'] = '$$WH.sprintf(LANG.lvnote_usercomments, '.$nFound.')'; - } - - $this->lvTabs[] = ['commentpreview', $tabData]; - } - - // Comment Replies - if ($_ = CommunityContent::getCommentPreviews(['user' => $this->user['id'], 'replies' => true], $nFound)) - { - $tabData = array( - 'data' => $_, - 'hiddenCols' => ['author'], - 'onBeforeCreate' => '$Listview.funcBox.beforeUserComments', - '_totalCount' => $nFound - ); - - if ($nFound > Cfg::get('SQL_LIMIT_DEFAULT')) - { - $tabData['name'] = '$LANG.tab_latestreplies'; - $tabData['note'] = '$$WH.sprintf(LANG.lvnote_userreplies, '.$nFound.')'; - } - - $this->lvTabs[] = ['replypreview', $tabData]; - } - - // Screenshots - if ($_ = CommunityContent::getScreenshots(-$this->user['id'], 0, $nFound)) - { - $tabData = array( - 'data' => $_, - '_totalCount' => $nFound - ); - - if ($nFound > Cfg::get('SQL_LIMIT_DEFAULT')) - { - $tabData['name'] = '$LANG.tab_latestscreenshots'; - $tabData['note'] = '$$WH.sprintf(LANG.lvnote_userscreenshots, '.$nFound.')'; - } - - $this->lvTabs[] = ['screenshot', $tabData]; - } - - // Videos - if ($_ = CommunityContent::getVideos(-$this->user['id'], 0, $nFound)) - { - $tabData = array( - 'data' => $_, - '_totalCount' => $nFound - ); - - if ($nFound > Cfg::get('SQL_LIMIT_DEFAULT')) - { - $tabData['name'] = '$LANG.tab_latestvideos'; - $tabData['note'] = '$$WH.sprintf(LANG.lvnote_uservideos, '.$nFound.')'; - } - - $this->lvTabs[] = ['video', $tabData]; - } - - // forum -> latest topics [unused] - - // forum -> latest replies [unused] - - $conditions = array( - ['OR', ['cuFlags', PROFILER_CU_PUBLISHED, '&'], ['ap.extraFlags', PROFILER_CU_PUBLISHED, '&']], - [['cuFlags', PROFILER_CU_DELETED, '&'], 0], - ['OR', ['user', $this->user['id']], ['ap.accountId', $this->user['id']]] - ); - - if (User::isInGroup(U_GROUP_ADMIN | U_GROUP_BUREAU)) - $conditions = array_slice($conditions, 2); - else if (User::$id == $this->user['id']) - array_shift($conditions); - - $profiles = new LocalProfileList($conditions); - if (!$profiles->error) - { - $this->addScript([SC_JS_FILE, '?data=weight-presets']); - - // Characters - if ($chars = $profiles->getListviewData(PROFILEINFO_CHARACTER | PROFILEINFO_USER)) - $this->user['characterData'] = $chars; - - // Profiles - if ($prof = $profiles->getListviewData(PROFILEINFO_PROFILE | PROFILEINFO_USER)) - $this->user['profileData'] = $prof; - } - } - - protected function generateTitle() - { - if (!$this->user) // shouldn't happen .. but did - return; - - array_unshift($this->title, Lang::user('profileTitle', [$this->user['username']])); - } - - protected function generatePath() { } -} - -?> diff --git a/setup/updates/1758578400_04.sql b/setup/updates/1758578400_04.sql new file mode 100644 index 00000000..7d6f7c5b --- /dev/null +++ b/setup/updates/1758578400_04.sql @@ -0,0 +1,17 @@ +ALTER TABLE `aowow_account` + CHANGE COLUMN `avatar` `wowicon` varchar(55) NOT NULL DEFAULT '' COMMENT 'iconname as avatar', + ADD COLUMN `avatar` tinyint(1) NOT NULL DEFAULT 0 COMMENT 'selected avatar mode' AFTER `userGroups`; + +DROP TABLE IF EXISTS `aowow_account_avatars`; +CREATE TABLE `aowow_account_avatars` ( + `id` mediumint unsigned NOT NULL, + `userId` int unsigned NOT NULL, + `name` varchar(20) NOT NULL, + `size` mediumint unsigned NOT NULL, + `when` int unsigned NOT NULL, + `current` tinyint unsigned NOT NULL DEFAULT 0, + `status` tinyint unsigned NOT NULL DEFAULT 0, + UNIQUE KEY `id` (`id`) USING BTREE, + KEY `userId` (`userId`) USING BTREE, + CONSTRAINT `FK_acc_avatars` FOREIGN KEY (`userId`) REFERENCES `aowow_account` (`id`) ON DELETE CASCADE ON UPDATE CASCADE +) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci ROW_FORMAT=COMPACT; diff --git a/template/pages/user.tpl.php b/template/pages/user.tpl.php index abf8dbbb..a18a3a48 100644 --- a/template/pages/user.tpl.php +++ b/template/pages/user.tpl.php @@ -1,7 +1,10 @@ - +brick('header'); ?> + use \Aowow\Lang; + $this->brick('header'); +?>
@@ -14,23 +17,28 @@ $this->brick('infobox'); ?> - +
+userIcon): +?>
-

name; ?>

+

h1; ?>

+ +

h1; ?>

+
-

user['description'])): +if ($this->description): ?>
-brick('lvTabs', ['relTabs' => true]); ?> +brick('lvTabs'); ?>