Единый форум поддержки

Информация о пользователе

Привет, Гость! Войдите или зарегистрируйтесь.


Вы здесь » Единый форум поддержки » Сделаем сервис лучше » Неглобальные доработки движка MyBB (с предложениями по PHP реализации)


Неглобальные доработки движка MyBB (с предложениями по PHP реализации)

Сообщений 61 страница 80 из 126

1

Доброго времени суток всем!
Давненько я не приходил на этот форум не по поводу проблем с форумами :D

Немного оффтопное вступление (много букв не по теме!)

Для тех, кто не знает, кто я такой и откуда взялся: я являюсь техническим администратором форумной ролевой игры, которой осенью исполнилось 7 лет, и которая на данный момент одна из немногих, кто продолжает работать в нашем фендоме, а в рейтинге форумов MyBB в своём разделе занимаем 8 место. Я не буду рекламить форум, не за этим я здесь. Сам я на MyBB уже 5 лет, за которые я вырос как программист в несколько десятков раз. Благодаря MyBB я стал хорошо разбираться в JavaScript, и сам начал писать сайты. Можно смело сказать, что эта платформа стала фундаментом моего роста, за что я благодарен Максиму и всем причастным данному движку.

Но наш форум растёт, появляются новые идеи, которым становится слишком откровенно тесно на MyBB. Ну слишком сильно ограничены мы в вопросе кастомизации форума. Менять вёрстку приходится через JS, которое либо в самом начале, когда ещё нечего изменять, либо в конце страницы, которое не всегда догружается быстро. Функционала полей профиля откровенно не хватает, так что часть информации мигрировала на отдельный сайт, рарабатываемый мной, и теперь подгружается через AJAX. А что ещё делать, если у лотам нужны комментарии, а к флажкам в полях профиля добавлять комментарии?

Сейчас примерно половина логики нашего форума не связана с платформой MyBB, из-за чего логика работы исказилась и стала путаться. Но отказаться от уже имеющихся решений мы не готовы, ибо это глупо. И старые вопрос четырёхлетней давности о переезде на собственный хостинг поднялся с новой актуальностью (раньше это было связано с DDoS, слава богу, это ушло), даже несмотря на откровенный упадок нашего фэндома.

За последние четыре года, на движке практически не произошло изменений, которые были бы полезны для моего основного форума здесь. Всё, что было полезно нам — это обновление jQuery, уведомление о ЛС и встроенный загрущик картинок без Flash. Ещё можно выделить мобильный стиль. Всё остальное — это хорошо, да, но... бли-ин. Последние обновления — визуальный редактор страниц и права доступа к ним. Хорошо, нам это не мешает, но и не помогает. Мобильный дизайн работает с нашим кастмным стилем работает слишком криво, а подправить его невозможно. Английская версия абсолютно бесполезна для русскоязычной FRPG.

В итоги, для нас MyBB перестал удовлетворять как движок, он отровенно устарел. Всё, что может нас удерживать здесь - это огромный объём данных и, что важнее, надежда на развитие сервиса. Но первый пункт и вовсе стал лишь вопросом "А захотим ли мы забрать все данные с MyBB при переезде, и в какое количество гемороя это может вылиться?". И теперь нас держит сейчас только надежда. Надежда, что движок перестанет быть мамонтом, эволюционирует и станет хоть чем-то, что можно будет администрировать без вечной головной боли. И эта надежда постепенно угасает, с каждым днём без действительно полезных для нас обновлений.

Предложения, которые я описал ниже, будут полезны не только для FRPG, но и для всех форумов на движке MyBB. Основано всё на реальных задачах, с которыми я сталкивался при работе над форумами и сопровождены предложениями по их реализации. Похожая тема — "Просилка", в которую я думал писать раньше, нынче скрывается за ошибкой "Ссылка, по которой Вы пришли неверная или устаревшая", и боле ничего о ней не слышно и не видно. Будем считать, что это "Просилка 2.0" :)

Изначально пост задумывался как запрос на исправление пары ошибок с тегами, но вырос в вот такой монструозный опус на тему "чего не хвататет на MyBB". Из-за этого нумерация нужна исключительно для ссылок и не несёт никакой иной информации.

1. Тег [hide] (предложения по доработке)

Тег скрытого текста, на самом деле, — одна из самый недоработанных функций на форумах MyBB.
С одной стороны, его полезность и важность невозможно переоценить, но при этом очень довольно плохо ведёт себя для модераторов и старожил форума.


1.1. [hide] и модераторы.

Давайте разберёмся, зачем вообще нужен [hide]: скрыть какую-то информацию от гостей/новичков. При этом скрывать эту инфу от модераторов раздела и администраторов бессмысленно: они его всё равно могут посмотреть через редактор сообщения. Ну и, конечно, автору сообщения. Это логично.

А вот нужно ли показывать содержимое тем модераторам, что не могут редактировать чужие сообщения в данном разделе? Движок MyBB в данном случае отвечает однозначно: надо, они ж модераторы. Но вот не всегда это полезно.

Например, анонимные голосования через тег [hide]. Пользователи пишут, за кого они голосуют и скрывают это. Однако модераторы, которые в данном случае должны иметь права обычных пользователей, видят голоса и становятся необъетивными.
Или ещё пример: темы в "админке" (специальном разделе для АМС). Иногда админам может понадобиться скрыть информацию от модераторов, например, пароль от аккаунта главного администратора (с id 2).

Что делать?
Конечно, кардинально менять логику тега не стоит. Однако опция в настройках к разделу форума была бы весьма полезна. Сомневаюсь, что добавить одну галочку в настройки сложно.

А вот с парсером чуть-чуть сложнее. Конечно, парсер не должен сильно рыться в настройках форума. Тем не менее, решение тут не особо сложное. Наверняка где-то рядом с вызовом парсера для печати в пост, находится булевая перменная, которая определяет, может ли пользователь редактировать данное сообщение. На основе этой переменной можно собрать ещё одну булевую переменную, которая на основе настройки раздела форума, права пользователя на редактирование и прочих параметрах:

Код:
$can_see_hide = 
    ($user["id"] == $post_author["id"]) || // показывать сообщение себе
    (($forum_settings["show_hide_tag_for_all_moderators"] == true) ? 
        ($user["groupid"] <= 2) : // Если галочка "Показывать [hide] всем модераторам" стоит, то просто проверяем группу
        ($user_allowed_to_edit_post)); // Если галочка не стоит, то смотрим, может ли пользователь редактировать сообщение

После чего отправляем это через global в парсер (или как-то иначе, я не знаю исходники) — и там уже на основе этой переменной и количества сообщений пользователя решаем, показывать ли содержимое или нет.


1.2. Лимит сообщений для открытого [hide].

Тут уже скорее вопрос удобства АМС и старожил форумов. Пользователи без прав просмотра отлично видят, сколько им надо сообщений для того, что бы открыть тег. Однако те, кто уже видит скрытие, не имеют возможности увидеть, какой лимит поставлен.

Что делать?
Если скрытый текст открывается, добавить в <cite> инфу о количестве сообщений, типа, "Скрытый текст (от 100 сообщений):..." Да, я знаю, что сейчас это связано с изменением языковых пакетов... Но разве добавить по 1 строчке в пакеты и добавить дополнительный тернарный оператор — это сложно?

2. Тег [align] (предложения по доработке)

Поведение этого тега — тоже та ещё задачка для пользователей, которые пытаются отформатировать сообщение. Все проблемы с ним тянутся от одного старого и, откровенно говоря, сомнительного решения парсить этот тег как строчный (в <span>), но отображать как блочный (с правилом display: block; text-align: something;). Из-за этого конфликта при разборе поведения тега пошли дичайшие неудобства, которые ощущаются до сих пор.


2.1. [align] и параграфы (предложения по доработке)

Самый заметный бред поведения тега — это его реакция на удвоенный перенос строки, воспринимаемый парсер как новый абзац. Из-за того, что [align] парсится в <span>, браузеры, увидев перекрёсный код типа:
<p>111<span>222</p><p>333</span>444</p>
поступают так, как им кажется правильным, и адаптируют невалидный HTML как
<p>111<span>222</span></p><p>333444</p>
В итоге, мы получаем сверхбредовое поведение: несмотря на то, что у нас тегом отмечены несколько параграфов, правильно отобразится только первый.

Что делать?
Собственно, главный способ решения этой проблемы — перестать парсить [align] как строковый тег. А во что парсить? Самое логичное — в блочный <p>. Конечно, это убьёт фичу, когда между двумя подряд идущими [align] нет отступа, но, откровенно говоря, это тоже смотрится как баг, пусть и более-менее юзабельный.
Сделать это можно примерно таким PHP кодом:

Код:
$code = "<p>111[align=center]222</p>".PHP_EOL."<p>333[/align]444</p>"; // Переменная, в которой хранится bb-код сообщения, который нужен для нас

$code = preg_replace_callback(
    "/\[align=(center|left|right|justify)\]([\s\S]*?)\[\/align\]/g", // Паттерн для тега align
    function($matches) {
        // $matches[1] - направление выравнивания, защищено от XSS
        // $matches[2] - код внутри, не жадный (до первого [/align])
        $tmp = explode("<p>", $matches[2]); // Разбиваем по параграфам...
        $tmp = implode("<p style=\"text-align: {$matches[1]}\">", $tmp); // И собираем параграфам с выравниванием!

        return "</p>".PHP_EOL."<p style=\"text-align: {$matches[1]}\">".$tmp."</p>".PHP_EOL."<p>";
    }, $code);

echo $code;
/*
<p>111</p>
<p style="text-align: center">222</p>
<p style="text-align: center">333</p>
<p>444</p>
*/

Что бы всё было красиво, остаётся только подставить вместо $code другую переменную, и вместо PHP_EOL — переменную с переносом строки и табуляциями (что б исходиники красивые были). Можно ещё и количество операторов снизить, избавившись от последовательного использования $tmp, но это как будет удобно программисту.

Можно заранее предположить, что где-то после внедрения этого поведения начнутся баги. В частности, сломается многострадальная часть парсера, избавляющаяся от "висячих" <br> и пустых <p>. Однако это решается просто: во всех паттернах, которые содержат в себе <p> нужно будет подравить под что-то типа <p(?: style=\"text\-align\: (center|left|right|justify)\")?> или <p(?:.*?)?>, если у нас на <p> будет вешаться что-то ещё (превентивный фикс поведения для предложния 3., что ниже).

Для тех, кто не знает, поведаю: паттерн (?:something)? можно использовать, что ообозначить показать, что тут может быть текст, удовлетворяющий этому паттерну something, но его может и не быть, при этом, несмотря на скобочки, он не будет запомнинаться.


2.2. [align] и переносы строк.

Эта проблема возникнит, если мы откажемся от решения проблемы методом из пункта 2.1., и примем, что тег [align] работает только в рамках одного параграфа. Но тут обнаружится, что тег всё равно ведёт себя странно, если рядом с ним окаывается переност строки.
Так как [align] ведёт себя как строковый тег, парсер не воспринимает наличие рядом с ним <br> как что-то неправильное. С его точки зрения всё довольно логично, так как
<p><span>111</span><br>222</p>
это абсолютно нормальный код для действительно строковых тегов, типа [b]. Однако <span> форматируется как блоковый элемент, из-за чего у нас возникает ломающий логику <br>:

111

Lorem ipsum dolor sit amet, consectetur adipiscing elit. Phasellus viverra eget mauris vel hendrerit. Integer lobortis hendrerit lacus a aliquet. Integer porttitor fermentum augue, quis fermentum augue lacinia eget.

В итоге, что бы такого разрыва не возникало, приходится писать текст в той же строке, что и [align]. Стоит ли говорить, что это мешает воспринимать сообщение в редакторе?

Что делать?
В этом варианте в паттерн тега [align] надо добавить проверку на то, что рядом есть переносы строк, в итоге паттерн тега станет примерно таким (центральная часть взята из 1 варианта):
/(?:<br>)?\[align=(center|left|right|justify)\]([\s\S]*?)\[\/align\](?:<br>)?/g - если разбор [align] идёт после преобразования \r\n в <br>;
/\s*\[align=(center|left|right|justify)\]([\s\S]*?)\[\/align\]\s*/g - если до.

3. Пользовательские BB-теги (новый функционал)

На MyBB много ролевых форумов, которым нужно, что бы в сообщениях что-то дополнительно показывалось. И на ЕТП довольно много скриптов, которые реализуют BB-коды. Но у всех этих реализаций есть один капитальный минус: если JavaScript не работает или очень тормозит, то пользователь видит неотформатированный текст. Сказать, что это хорошо опредённо нельзя, хотя жить с этим можно.

Тем не менее, некоторые BB-теги не требуют значительных усилий для реализации: лишь самым навороченным из них нужно что-то кроме банальных паттернов. А вот решительное большинство пользовательских BB-тегов можно реализовать довольно безболезнено. Да, конечно, потребуется доработка базы данных, однако доработка заключается в добавлении одной таблицы, что явно не намного сложнее уже древнего обновления с новыми типами пользовательских полей от апреля 2011.


3.1. Настройка пользовательских BB-кодов

Тут, всё очень просто. То, что админка форумов более-менее настраиваема, мы знаем из июньского обновления со скриптами в админке. Поэтому, для пользовательских BB-кодов просто добавляем 2 страницы в админку.

(Придумано после описания и добавлено так, что бы не удалять нормальный текст) В теории, весь раздел можно сделать на основе /admin_pages.php.

3.1.1. Список пользовательских BB-кодов
Во-первых, поле создания BB-кода. Тут можно сделать поле и кнопку "Создать", как на странице /admin_categories.php. После нажатия на кнопку должна открываться страница настройки нового bb-кода (см. 3.1.2.).

Во-вторых, список уже созданных BB-кодов. Не думаю, что кому-то нужно его сортировать, так что можно отображать в алфавитном порядке. Рядом с каждым нужна кнопочка "редактировать", как на /admin_forums.php.

3.1.2. Редактирование BB-кода
Эта страница так же не содержит откровенно нового.

1. Название bb-кода. Именно то, что будет в парсится из квадратных скобкок. Разрешаем тут только английские символы. Цифры, дефис, подчёркивание — можно, но не обязательно. А вот русские буквы, пробелы, плюсики и прочую пунктуация посылаем нафиг. Хотя на некоторых движках используется [*] как разделитель элементов списков <ul>...
2. Видимость в редакторе: Да/Нет. Отображать ли кнопку над полем редактирования сообщения с данным bb-кодом.
3. Иконка bb-кода. Сюда нужна только ссылка. Если это поле не пустое, будем показывать bb-код как кнопку. Если пустое, то спрячем под кнопку "Дополнительно". Размер картинки не важен, всё равно в CSS-е мы ограничивать будем. Заливать картинки можно через "Файлы", на uploads или ещё как-нибудь.
4. Тип: Без параметра/С параметром. Определить, как будет вести себя bb-код: как [i] или как [font]. Можно, конечно, сделать комбинированный вариант (как [hide]) и с несколькими параметрами (как [table])... Но это, на самом деле, уже откровенный избыток функционала. Нафиг, нафиг, нафиг.
5. Замещающий текст. Собственно, второй параметр для preg_replace. Можно, для удобства пользователей, использовать не {0} и {1}, а, например, {param} и {content}, так как так ясно, что где.
6. Комментарий к параметру (только, если у нас тип "С параметром" и видимость в редакторе включена). То, что будет отображаться при нажатии на кнопку тега в prompt-диалоге.

Так как код редактирует админ, защищаться от XSS нам не особо нужно: есть много более простых способов сломать форум будучи админом, а в область PHP мы всё равно никого не пустим (жаль, но да ладно). Аналогичный вывод следует для проблемы потенциальной сломанной вёрстки.

Собственно, на основе этих полей легко можно понять, что нужно в SQL-таблице: 5 полей (может быть 6, если не делать ключевым полем название тега).


3.2. Парсинг пользовательских BB-кодов

Тут, на самом деле, всё довольно просто. Перед парсингом постов, подгружаем из БД (или кеша) название (будем называть это поле name), тип (type) и замещающий текст (replacer) всех BB-кодов в массив, скажем, $userbbs. Через global пропихиваем перменную в функцию парсера, и ближе к концу, после обработки всех тегов, но перед отчитской пустых тегов (что бы у нас не остались висеть пустые параграфы), добавляем что-то типа такого:

Код:
$code; // тут у нас BB-код

foreach($userbbs as $userbb) {
    if ($userbb['type'] == 0) {
        // Без параметров
        $pattern = "/\[{$userbb['name']}\]([\s\S]*?)\[\/{$userbb['name']}\]/g";
        $replacer = str_replace('{content}', '{0}'), $userbb['replacer']); // Тут одинарные кавычки, что б PHP не начал воспринимать {content} как попытку подставить переменную
    }
    else if ($userbb['type'] == 1) {
        // С 1 параметром
        $pattern = "/\[{$userbb['name']}=\"?([\s\S]*?)\"?\]([\s\S]*?)\[\/{$userbb['name']}\]/g";
        $replacer = str_replace(array('{param}', '{content}'), array('{0}', '{1}'), $userbb['replacer']);
    }
    else {} // Если есть желание делать ещё типы

    $code = preg_replace($pattern, $replacer, $code);
}

echo $code;

3.3. Добавление кодов в редактор

Тут тоже не сказать, что какой-то сложный код.

В конце <head> инициализируем дополнительные кнопки (в JSON добавляем только видимые теги, см. 3.1.2.2.):

Код:
<style id="userbbs-style"></style>
(function(userbbs) {
    var css = "";
    for(var i = 0; i < userbbs.length; i++) {
        var bb = userbbs[i], obj = { name: bb.title };
        if (bb.param) {
            obj.onclick = function() { bbcode('[' + bb.name + '="' + prompt(bb.prompt_text, '') + '"]','[/' + bb.name + ']'); }
        }
        else {
            obj.onclick = function() { bbcode('[' + bb.name + ']','[/' + bb.name + ']'); }
        }
        if (bb.icon != '') {
            FORUM.set('editor.' + bb.name, obj);
            css += "td#button-font {background:url(" + bb.icon + ") no-repeat center center; background-size: 26px 26px}\r\n"
        }
        else {
            FORUM.set('editor.addition.tags.' + bb.name, obj);
        }
    }
    $("#userbbs-style").html(css);
})(
[ // Начало JSON с инфой о тегах
    {"name":"mytag", "title":"Мой bb-код", "icon": "http://.../icon.png", "param": true, "prompt_text": "Параметр к моему bb-коду"}
] // Конец JSON с инфой о тегах
)

Можно генерить JS для FORUM.editor и CSS через PHP — вообще не принципиально, суть ясна.

В итоге, на форумах появится довольно удобная и функциональная система для работы с BB-кодами. Можно придумывать на неё навороты, но зачем? Если нужно будет редактировать что-то, то можно будет корректировать этот код через JS (предварительно, сгенерив через рандом уникальный ID)... Окошко при редактировании сообщений тоже добавляется достаточно просто: переопределением функции FORUM.editor.mytag.onclick. И 99.9% задач с BB-кодами решены!

4. JavaScript (jQuery?) Hooks (новый функционал)

Ещё одна большая проблема MyBB, с которой сталкивается любой разработчик скриптов для MyBB — проблема со скриптами, обрабатывающими страницу, которая выражается в том, что скрипт из HTML-низа, обрабатывающий страницу, не запустится, пока не загрузится вся страница и не выполнятся скрипты перед ним.
Например, на нашем форуме есть очень важный скрипт, который обрабатывает поля профиля в специальное окошко с информацией о персонаже (весьма востребованная штука на ролевых форумах, стоит отметить: скрипт Deff'а, реализующий нечто подобное, используют многие). Однако в больших темах (где играют "бешенные" игроки, пишущие по 10-20 тысяч символов) и/или при не особо быстром интернете, этот скрипт не может подготовить "столбик автора" весьма значительное время, и пользователи видят необработанные поля. Опять-таки, жить можно, но как-то не особо удобно. Да и HTML-низ на многих форумах превращается в грандиозную свалку во многом по этой причине.

На одном из движков, которые я рассматривал как альтернативу MyBB (а точнее, на mybb.com), была система плагинов, основанная на использовании т.н. "крючков" (hooks), которые вызывали функции плагинов, когда это было нужно. Там она относилась к серверной составляющей, однако эту удобную систему можно перенести на наш MyBB как помощь разработчикам JavaScript.

Тут, в принципе, есть 2 способа, как это сделать: при помощи jQuery или при помощи простого JavaScript и объекта FORUM, которые отличаются только кодом.


4.1. Общие детали

По факту, здесь можно реализовать пользовательские события. То есть схема примерно такая:
1. Администратор в html-верху регистрирует функции (handlers), которые должны быть применены после загрузки какого-либо элемента.
2. Когда пользователь грузит тему, после каждого сообщения вызываются функции, привязанные к данному событию.

Схема проста, но чрезвычайно полезна. Эти хэндлеры можно спокойно запустить параллельно, так что сильно грузить страницу они не будут (хотя если случится зацикливание, будет грустно, но это уже на совести администраторов).


4.2. JavaScript

В принципе, ничего сверхестественного тут выдумывать не надо:

Код:
FORUM.hooks = {
    _events: {},
    register: function(name, callback) {
         if('undefined' == typeof(FORUM.hooks._events[name]))
             FORUM.hooks._events[name] = [];
         FORUM.hooks._events[name].push(callback);
    },
    call: function(name, arguments) {
        if('undefined' != typeof(FORUM.hooks._events[name]))
            for(var i = 0; i < FORUM.hooks._events[name].length; i++)
                FORUM.hooks._events.apply(null, arguments || []);
    }
}

Просто, коротко и, что самое главное, действенно.

Далее, в коде странице, например, после загрузки каждого сообщения, вставляем вставить примерно такой код:

Код:
<script>FORUM.hooks.call('post', [ 12345 ]);</script>

где 12345 - это id сообщения.

Теперь всё, что нужно сделать администратору - это зарегистрировать событие:

Код:
FORUM.hooks.register('post', function(pid) {
    console.log("Только что загрузилось сообщение #" + pid);
});

И, вуаля, в консоле покажется все сообщения, что есть на странице.


4.3. jQuery

В jQuery этот код получается несколько проще. Всё делается через функции on и trigger:

Код:
// Регистрация события админом
$(document).on('FORUM-post', function(e, pid) {
    console.log("Только что загрузилось сообщение #" + pid);
});

// Вызов
$(document).trigger('FORUM-post', [ 12345 ]);

4.4. На что надо развесить "крючки"?

Сообщения, в том числе в ЛС, при поиске и предпросмотре в редакторе;
Редактирование профиля (в первую очередь, в графе "Дополнительно");
Форума, точнее, строки с форумами на главной странице (для скрипта аватарок);
Темы, на страница поиска и списка тем форума (для скрипта аватарок);
• после генерации кнопок редактора, что бы можно было изменять их порядок сразу же после генерации;
• после пользовательского BB-кода (не уверен, <script> можно запихнуть и в сам bb-код).

В принципе, чем больше будет мест, к которым можно будет прицепиться "крючком", тем лучше, но, ясное дело, что документирвоать это всё будет заморочно.

5. Поле профиля с настройками отображения скриптов (новый функционал) Уже в планах

Ещё один гигантский пласт скриптов - это скрипты, которые добавляют различные украшательства на форум: снежинки, уведомления о ЛС, переключалки стилей и т.д.

Я не случайно назвал как пример эти 3 скрипта. У них есть одна общая черта — они настраиваются. И тут случается тотальный геморой для всех скриптёров: на сервисе тупо нет никакой системы хранения настроек для скриптов на сервере.
Откровенно говоря, это очень странно. Скриптёрам приходится использовать cookie, LocalStorage для хранения настроек отображения... Но это едва ли не апофеоз костыльности скриптов для MyBB. Мало того, что cookie и LocalStorage позволяют хранить отображение только в одном месте (тогда как у некоторых людей аж по 5 мест, откуда они пользуются форумом: планшет, телефон да 3 компьютера: дома, на работе и походный ноут), так ещё эти штуки у многих очищаются после определённого времени! В итоге у пользотелей начинют сбрасываться стили, включатся снежинки и начинают орать уведомления, что явно не вызывает хорошего настроения от пользования форумом.

Правильное решение для этой проблемы — просто дать каждому пользователю бесплатное поле профиля, в котором будет хранится JSON с настройками. Этот JSON можно тупо вставить в <head>, где перечисляются различные переменные типа UserName. И тогда каждый скрипт сможет прочесть оттуда нуждную информацию: включены ли снежинки, какая громкость уведомления, какой стиль включён.


5.1. Ограничения

Кто-то может справедливо заметить, что дополнительное поле для всех пользователей и форумов — это потеря денег для платформы. Я же на это отвечу, что за нормальный функционал можно и заплатить. Правда, хотелось бы, что это поле осталось бесплатным, оставив некоторые ограничения.

Ограничения, вообще говоря, уместны. Во-первых, администратор должен сам прописывать, какие ключи может иметь объект с настройками. Во-вторых, возить трафик через это поле — затея скверная с любой стороны, поэтому каждое значение можно ограничить, скажем, 100 символами. Если скрипту понадобится много настроек, то скриптёр может использовать несколько ключей или как-то сжимать данные. В-третьих, можно ограничить количество ключей, которые можно использовать. В-четвёртых, это поле нельзя будет редактировать напрямую.

Эти ограничения позволят не забивать это поле спамом. При этом полезность поля будет запредельная.


5.2. Как это можно реализовать

В JavaScript переменные форума (что в <head>), можно добавить переменную UserViewSettings с объектом, который извлекается из этого поля. Скрипты могут спокойно воспользоваться ими.

Список разрешённых ключей можно редактировать через админку. Любой способ отображения и редактирования массива строк подойдёт: одно текстовое поле с правилом "1 строка - 1 элемент" или же что-то интерактивное, как, напирмер, работа с элементами поля профиля типов "Флажок" или "Переключатель". Это не принципиально. Хранить массив тоже несложно: либо как JSON, либо просто через символ-разделитель (перенос строки или запятую).

Интереснее будет с сохранением этого поля. Тут есть 2 варианта реализации... И реализовать можно оба сразу, хуже не будет.

5.2.1. GUI через профиль
На какую-нибудь страницу редактирования профиля (либо /profile.php?section=display, либо на какую-то новую) добавляем несколько полей ввода, которые будут обозначать пары ключ-значение из скрипта. Через JS это поле можно будет сделать невидимым и сделать настройки красивыми.
Если предложение 4 с крючками реализовано, то сюда тоже можно приделать точку "зацепа".

5.2.2. API
Многострадальное API MyBB изначально имела огромный потенциал, но уже долгое время простаивает без изменений. А жаль, так как идея очень хороша...
Данное поле — отличный кандидат на то, что бы стать первым местом, где появится метод POST. Тут стоит отметить, что если мы делаем вызов со страницы сайта, то через AJAX будут переданы все cookie и данные сессии. А значит проверить пользователя не составит никаого труда.

Итак, мы запускаем через JS такой код:
$.post("/api.php?method=viewsettings.set&key=mykey", [ data: 'mydata' ], function(data) { if (data.success) { UserViewSettings = data.data; myscript_use_settings(); } else { console.log(data.error); }});

На сервере мы проверяем, залогинен ли пользователь и разрешено ли использовать ключ mykey. Если всё хорошо, мы сохраняем данные и возвращаем объект типа

Код:
{
"success": true,
"data": {"mykey":"mydata","another":"something"}
}

Если же что-то пошло не так, то пишем

Код:
{
"success": false,
"error": "Запрещённый ключ/Неавторизован и т.д."
}

Кстати, тут тоже можно использовать "крючки" из предложения 4 :D

6. Профиль пользователя (предложения по доработке)

На данный момент, самая тяжёлая для разработки страница — это страница просмотра профиля. Если говорить откровенно, она реализована так плохо, что её практически невозможно настроить. В добавок, если вы сидите с аккаунта главного администратора, то вы просто никогда не увидите эту страницу, и будете вспоминать о ней только когда начнут возмущаться пользователи. И то, для работы с ней потребуется либо выйти с аккаунта, либо открыть ещё один браузер. Мягко говоря, это неудобно.


6.1. Просмотр профиля для всех

Да, это действительно нужно. Почему, перейдя из списка персонажей в аккаунт пользователя, которого я могу править... Я вижу страницу его правки, а не просмотра?! Я не хочу его изменять сейчас! Это абсолютно нелогично!

Собственно, что можно сделать? Да всё просто.
/profile.php?id=123 — просмотр профиля профиль
/profile.php?id=123&section=view — тоже просмотр профия
/profile.php?id=123&section=essentials — редактирование профиля

При таком варианте надо менять минимальное количество вещей. Просто значение $_GET["section"] принимать по умолчанию (при пустой строке) не essentials, а view. Соответственно, в ветку if ($_GET['section'] == 'view') {} перенести код просмотра профиля. Ну и, соответственно, добавить ссылку "Просмотр/View" в начале менюшки пользователя.
Само боковое меню с ссылками можно и оставить, профиль практически всегда будет умещаться.

В итоге все страницы останутся доступны по старым ссылкам с section, но у админов хотя бы появится возможность просто посмотреть профиль.


6.2. Вёрстка полей профиля

Тут, в принципе, менять надо довольно много.

6.2.1. Вёрстка "столбца автора"
В первую очередь, обратимся к этому полю. Почему нельзя сделать так, что бы название поля и значение хоть как-то различались??! Это редактировать реально не долго: всего-лишь изменить вёрстку
<li id="pa-{field_id}">{field-name}: {field-value}</li>
на
<li id="pa-{field_id}"><span>{field-name}:</span> <strong>{field-value}</strong></li>
Другими словами, вёрстку внутри поля взять со страницы просмотра профиля.

Такой код можно нормально отформатировать без использования скриптов — так, как и должен работать дизайн. Добавление нескольких span вообще не ломает вёрстку, но зато этот код можно отформатировать, например, в табличку (как сейчас при просмотре профиля). Или сделать названия полужирными. Или значения полужирными. Отдельно друг от друга. И перечислять все плюсы тут можно крайне долго.

В добавок, скриптёрам, которые обрабатывают поля профиля, станет намного проще редактировать поля профиля

6.2.2. Табличная вёрстка страницы просмотра
САБЖ. Я, конечно, всё понимаю, но этого я не понимаю. Почему нельзя сделать здесь сделать вёрстку такую же, как у сообщений на форуме: простым float?! Да, вёрстка
<ul><div><li>...</div><div><li>...</div></ul>
это не очень хорошо, но то, что есть сейчас — ещё хуже!

6.2.3. ID полей на странице просмотра
Тут всё просто: их нет. Ладно, они есть у имени и у статуса — хоть что-то. Но почему Ни у одного поля нет этого важного аттрибута? Из-за этого кастомизировать эту страницу очень сложно. При этом редактировать эти поля хочется: на ролевых формуах пользовательские поля стилизуются под свои нужды, и тут это тоже нужно.

6.2.4. Аватарка
Совсем незначительная правка, но раз уж начал... Здесь можно, и нужно обойтись без <div>. В темах же обходимся.

Это далеко не всё, что можно сделать. Есть даже мысли о том, как сделать PHP-плагины, однако это долго, сложно и с негарантированной защитой от бекдора, а значит дальше мыслей может банально не уйти.

P.S. Приношу извинения, если кто-то засхлебнулся кровью из глаз из-за моей орфографии. Писался сей опус как поток мыслей, и я не особо редактировал. Прастити (>__<)
И пните меня, если где-то капитально накосячил.

Отредактировано kozhilya (Чт, 9 Фев 2017 23:30:56)

+8

61

Так. Продолжаю ковырять парсер в попытках реализовать пункт 3 из этой своей темы, касающихся пользовательских тегов. В итоге, пришёл к 2 выводам.
1) Отдельная страница и таблица — это хорошо и круто, но перебор.
2) Мне нравится ковырять парсеры :D
И если второе к делу отношения имеет мало, то вот с первым дело сложнее.

На данный момент я пришёл к выводу, что для хранения информации о пользовательских тегов можно использовать довольно короткий и ёмкий мини-язык разметки.

Запретный эльфийский язык Формальное описание синтаксиса разметки, к которому я пришёл, в виде набора БНФ-правил
Wikipedia написал(а):

БФН (сокр. БНФ, Бэкуса — Наура форма) — формальная система описания синтаксиса, в которой одни синтаксические категории последовательно определяются через другие категории.

<code> ::= <tag> <html_settings>? <flags>?
<tag> ::= <word>
<html_settings> ::= "[" <html_tag>? <html_attr>? "]"
<html_tag> ::= <word> (["." <word>])*
<html_attr> ::= "/" <word_and_minus>
<flags> ::= ":" <letters>
<letters> ::= ([a-z])+
<word> ::= ([a-z] | [0-9])+
<word_and_minus> ::= ([a-z] | "-")+

Если содержимое спойлера выше для вас выглядит как филькина грамота, не волнуйтесь, что-то не так не с вами, а со мной :D

Этот набор правил описывает довольно компактную форму записи для всего того, что я описал у себя выше. Приводя всё в более человеческий вид, то я придумал записывать правила для формирования пользовательского тега в формате:
тег[элемент.класс/аттрибут]:флаги
Далее вместо сухого объяснения я всё-таки предпочту разбить всё на 3 группы и подкрепить всё наглядными примерами.

База bb-кода: флаги s, a и m
  • s (от single) – флаг одиночного кода. С этим флагом не будет добавлена проверка закрывающего тега.

  • a (от attribute) – у тега есть параметр после знака "=" в открывающем теге. Не делает ничего, если используется флаг m.

  • m (от mixed) – у тега может принимать параметр сели он есть, а также без него. Полностью перекрывает действие флага a.

tag

[tag]content[/tag]

<div class="custom_tag custom_tag_tag"><p>content</p></div>

tag:s

[tag]

<div class="custom_tag custom_tag_tag"></div>

tag:a

[tag]content[/tag]

[tag]content[/tag]

[tag=param]content[/tag]

<div class="custom_tag custom_tag_tag" alt="param"><p>content</p></div>

tag:m

[tag]content[/tag]

<div class="custom_tag custom_tag_tag"><p>content</p></div>

[tag=param]content[/tag]

<div class="custom_tag custom_tag_tag" alt="param"><p>content</p></div>

Параметры вёрстки: настройка тегов, атрибутов и флаг строчности i

После названия тега может быть включены дополнительные данные по html. Они оборачиваются в квадратные скобки и содержать разделение в виде косой черты "/". То, что содержится до косой черты (либо всё содержимое, если его нет), воспринимается как декларация тега и дополнительных классов. То, что содержится после косой черты - как атрибут, в который будут помещёны данные аргумента тега (если он есть).

По умолчанию, парсер считает, что пользовательский тег является блочным, и разбивает параграф, в котором находится. Для того, что бы изменить это поведение, нужно добавить флаг i (от inline). Этот флаг также заменяет выставляемый тег на span, но только если не задан другой тег.

tag

before [tag]content[/tag] after

<p>before</p>
<div class="custom_tag custom_tag_tag"><p>content</p></div>
<p>after</p>

tag[pre]

before [tag]content[/tag] after

<p>before</p>
<pre class="custom_tag custom_tag_tag"><p>content</p></pre>
<p>after</p>

tag:i

before [tag]content[/tag] after

<p>before <span class="custom_tag custom_tag_tag">content</span> after</p>

tag[kbd]:i

before [tag]content[/tag] after

<p>before <kbd class="custom_tag custom_tag_tag">content</kbd> after</p>

tag[i.fa]:i

[tag]content[/tag]

<i class="custom_tag custom_tag_tag fa">content</i>

tag[.float]

[tag]content[/tag]

<div class="custom_tag custom_tag_tag float"><p>content</p></div>

tag[/data-value]:m

[tag=param]content[/tag]

<div class="custom_tag custom_tag_tag" data-value="param"><p>content</p></div>

tag[iframe/href]:sa

[tag=param]

<iframe class="custom_tag custom_tag_tag" href="param"></iframe>

Обработка данных: флаги u и e.
  • u (от unique) – тегу будет дан уникальный id.

  • e (от event) – после включения обработанного элемента, будет вызвано Jquery-событие. Также повторяет действие флага [u], даже если он не установлен.

Если используется один из этих флагов, и в качестве целевого атрибута указан id, то в id будет записан уникальный идентификатор, а данные будут записаны в атрибут alt.

tag

[tag]content[/tag]

<div class="custom_tag custom_tag_tag"><p>content</p></div>

tag:u

[tag]content[/tag]

<div class="custom_tag custom_tag_tag" id="custom_tag123456"><p>content</p></div>

tag[/id]:ua

[tag=param]content[/tag]

<div class="custom_tag custom_tag_tag" id="custom_tag123456" alt="param"><p>content</p></div>

tag:e

[tag]content[/tag]

<div class="custom_tag custom_tag_tag" id="custom_tag123456"><p>content</p></div>
<script>jQuery(document).trigger(jQuery.Event("custom_tag",{"selector":".custom_tag#custom_tag123456","tag_name":"tag"}));</script>

Прочие флаги.
  • t (от trim) – горизонтальные пробелы по краям содержимого тега будут удалены.

  • o (от trim outside) – горизонтальные пробелы вокруг тега будут удалены.

Для удобства восприятия и защиты кода в примерах ниже символ подчёркивания (который "_") будет означать пробельный символ

tag:i

before__[tag]__content_content__[/tag]__after

<p>before__<span class="custom_tag custom_tag_tag">__content_content__</span>__after</p>

tag:it

before__[tag]__content_content__[/tag]__after

<p>before__<span class="custom_tag custom_tag_tag">content_content</span>__after</p>

tag:io

before__[tag]__content_content__[/tag]__after

<p>before<span class="custom_tag custom_tag_tag">__content_content__</span>after</p>

tag:ito

before__[tag]__content_content__[/tag]__after

<p>before<span class="custom_tag custom_tag_tag">content_content</span>after</p>


  • n (от nested) – тег будет корректно работать, если теги вложены друг в друга.

tag:i

before[tag]content1[tag]content2[/tag]content3[/tag]after

<p>before<span class="custom_tag custom_tag_tag">content1[tag]content2</span>content3[/tag]after</p>

tag:in

before[tag]content1[tag]content2[/tag]content3[/tag]after

<p>before<span class="custom_tag custom_tag_tag">content1<span class="custom_tag custom_tag_tag">content2</span>content3</span>after</p>

Пока выходит так. Ещё приведу пару более изящных решений для реализации уже имеющихся bb-кодов.

indent

Да, можно накрутить и более сложный вариант, но начнём с простого. Правило тега: intend:si. То есть одиночный (s) строковый (i) тег.

Добавляем немного css:

Код:
.custom_tag_intend {
    display: inline-block;
    width: 1.2em;
}

И, вуаля! Получилась красота :) И js не используется вообще!

https://i.gyazo.com/546e1653820cbeff1754a0b290a5e4ae.png

float

Более интересный тег. Для него используем правило float[/id]:a. То есть парный (нет s) блочный (нет i) тег с обязательным параметром (a), который будет помещён в аттрибут id ([/id]).

Добавляем ещё щепотку css:

Код:
.custom_tag_float#left {
    float: left;
}
.custom_tag_float#right {
    float: right;
}

https://i.gyazo.com/99a5fbb4a0b3e511ec5af07ca1852e23.png

А дальше я уже устал сочинять примеры :D Суть, надеюсь, ясна.

Собственно, пока это доступно только на моём тестовике, так что пощупать в живую не выйдет, но ставлю на повестку несколько вопросов:

  • Что я мог забыть важного? И, может быть, стоит поменять

  • Стоит ли добавлять дополнительные флаги? Например, может быть будет полезно "вытравлять" окружающие код пробельные символы, так как для строчных тегов они могут создавать не самые приятные коллизии.

  • Стоит ли заморачиваться над UI? Теоретически, не обязательно даже вкручивать его в php, можно оставить на уровне js с последующей сборкой в эту сильно формализованную грамматику.

Отредактировано kozhilya (Пн, 3 Авг 2020 18:03:39)

+5

62

kozhilya написал(а):

тегу будет дан уникальный id.

По идее интересно давать уникальный ID как ''+postID+UserId+N - номер вставляемого тега c начала сообщения, для того чоб можно пользоваться инфой о postID и UserId сделать их фиксированной максимальной длины, заполняя нулями ?

Отредактировано Deff (Пн, 3 Авг 2020 18:20:34)

0

63

Ну и ыщо соображения: Для своих задач верстки мне пока вполне хватает  тега [block=class], ну кроме тут намеченного тега iframe,
Ибо тег block позволяет использовать несколько классов [block=aa bb cc]( один класс может быть для строчности-блочности, второй для float и тд...

Отредактировано Deff (Пн, 3 Авг 2020 18:30:44)

0

64

Deff
М... Попробую посмотреть. Но, по идеи, оно не требуется, так как всё уже включено в .post, и достать это можно через

Код:
let post = $(event.selector).parents('.post');
let user_id = post.data('user-id');
let post_id = post.attr('id').substr(2);

+1

65

kozhilya написал(а):

М... Попробую посмотреть. Но, по идеи, оно не требуется, так как всё уже включено в .post, и достать это можно через

Ну ежли теги обрабатываешь на всей странице или всей теме сразу, как то существенно экономит код в скрипте, хотя тут нун подумать о разрастании кода передачи страницы ( я про добавку нулей), если это существенно - то забить  :flag:

Отредактировано Deff (Пн, 3 Авг 2020 18:34:43)

0

66

Хотя как вариант, разделять не нулями, а буквами
773+'a'+87763+'b' + N - номер тега в посте

0

67

Deff
Я не думаю, что добивка нулями имеет хоть какой-то смысл. Если и прокидывать, то либо в data-атрибуты самого тега, либо в виде полей объекта события... Да, попробую протолкнуть, наверное.

+2

68

kozhilya написал(а):

Мне нравится ковырять парсеры

дам 2 ссылки на разные парсеры на родственных движках, возможно будут полезными:
1. FluxBB_by_Visman (он весьма заморочился с бб-кодами списков)
2. Flazy (в этом присутствует бб-код wiki)

kozhilya написал(а):

Стоит ли заморачиваться над UI?

пока наверное нет

0

69

Добавил в свой набросок описание флагов t, o и n. Продублирую сюда, так как спойлеры немного сломаны :D

Спойлер
  • t (от trim) – горизонтальные пробелы по краям содержимого тега будут удалены.

  • o (от trim outside) – горизонтальные пробелы вокруг тега будут удалены.

Для удобства восприятия и защиты кода в примерах ниже символ подчёркивания (который "_") будет означать пробельный символ.

tag:i

before__[tag]__content_content__[/tag]__after

<p>before__<span class="custom_tag custom_tag_tag">__content_content__</span>__after</p>

tag:it

before__[tag]__content_content__[/tag]__after

<p>before__<span class="custom_tag custom_tag_tag">content_content</span>__after</p>

tag:io

before__[tag]__content_content__[/tag]__after

<p>before<span class="custom_tag custom_tag_tag">__content_content__</span>after</p>

tag:ito

before__[tag]__content_content__[/tag]__after

<p>before<span class="custom_tag custom_tag_tag">content_content</span>after</p>


  • n (от nested) – тег будет корректно работать, если теги вложены друг в друга.

tag:i

before[tag]content1[tag]content2[/tag]content3[/tag]after

<p>before<span class="custom_tag custom_tag_tag">content1[tag]content2</span>content3[/tag]after</p>

tag:in

before[tag]content1[tag]content2[/tag]content3[/tag]after

<p>before<span class="custom_tag custom_tag_tag">content1<span class="custom_tag custom_tag_tag">content2</span>content3</span>after</p>

+3

70

Встал вопрос реализации цветовыделения по группам средствами css, и оказалось, что в разделе "Активны" не хватает класса с группой отдельно взятого пользователя. Было бы замечательно, если бы он тоже был сюда добавлен, как это сделано в статистике.

Свернутый текст

https://forumupload.ru/uploads/0000/14/1c/34418/243513.png

+1

71

По мотивам:
http://forum.mybb.ru/viewtopic.php?id=3 … 89#p962378

kernel, не могли бы вы сделать так, как пишет audaciousGodsend:

Для онлайна в ссылках внутри #onlinelist, к сожалению, отсутствует данный класс, но можно попросить @kernel, чтобы class="groupN" тоже добавили в раздел "Активны". (Это требуется сделать через правку ядра движка).
.... Тогда можно будет реализовать цветовыделение и там без помощи скрипта.

Тогда можно будет полноценно окрасить ники групп в статистике.

https://i.imgur.com/iOcjpol.jpg

+1

72

audaciousGodsend
Hope13
вы дублируете, то о чём уже писали Новые селекторы

+2

73

Romych
Не отследила, прошу прощения.
Тогда сообщения можно зачистить и спокойно ждать реализации )

+1

74

@kernel Иван, а можно было бы сделать возможность добавлять к таблице класс, по принципу как для блока? Для более точечной работы с таблицами в постах

Код:
[table=class layout=fixed width=100%]
[tr]
[td][/td]
[/tr]
[/table]

+2

75

Romych написал(а):

@kernel Иван, а можно было бы сделать возможность добавлять к таблице класс, по принципу как для блока? Для более точечной работы с таблицами в постах

Код:
[table=class layout=fixed width=100%]
[tr]
[td][/td]
[/tr]
[/table]

А зачем?

Код:
[block=class]
[table layout=fixed width=100%]
[tr]
[td][/td]
[/tr]
[/table]
[/block]
<style>.class table {}</style>

+3

76

kernel написал(а):

А зачем?

ну да согласен, тоже до этого додумался 2 часа назад

+2

77

kozhilya
Добра!
Есть вопрос про новый вариант форматирования [align], меня отправили сюда)
Переключил у себя форматирование [align] на «Новый вариант (параграфы)» и обнаружил странный баг.
У меня есть отцентрованный текст, который является названием спойлера. Так вот там сверху и снизу добавились пустые <p> почему-то, судя по коду страницы, и спойлеры визуально разрослись.

Выглядит это так:
А это для сравнения: спойлер с отцентрованным текстом и с текстом по левому краю

Ссылка на тему со скрина, чтобы пощупать, вот. Но можно и сразу тут пощупать:

Отцентрованный текст

Текст

Неотцентрованный текст

Текст

Вопрос такой: это баг или фича? Для меня выглядит как баг)

+1

78

Согласен с постом выше :flag: captainspring
Та же беда. Как исправить?

0

79

captainspring
Да, знаю о проблеме, но пока у меня нет времени её исправить... Постараюсь решить на следующей неделе.

+1

80

captainspring
Ну как пока костыль в стиль:

.spoiler-box>div[onclick] p:empty{
  display:none;
}

   :flag:

+1


Вы здесь » Единый форум поддержки » Сделаем сервис лучше » Неглобальные доработки движка MyBB (с предложениями по PHP реализации)