Задать вопрос
  • Как заставить PHPStorm кушать меньше памяти?

    @hjk Автор вопроса
    Всё оказалось просто и тупо. Оставлю, если кому будет интересно. Шторм индексировал папку с логами проекта, которые оказались включены. Он пытался этот рост заиндексировать прямо в реальном времени и закипал. Оказалось достаточно исключить папку логов из индекса, и всё вернулось на круги своя.
    Ответ написан
    1 комментарий
  • Как исправить ошибку при подключении к MySql через JDBC?

    Shockoway
    @Shockoway
    Скорее всего есть какой-то более корректный путь, но я лечил так:
    "jdbc:mysql://[хост]:[порт]/[бд]?useUnicode=true&useJDBCCompliantTimezoneShift=true&useLegacyDatetimeCode=false&serverTimezone=UTC"
    Ответ написан
    2 комментария
  • Активация/деактивация swiper при ресайзе окна браузера?

    @artuh_a
    Общая идея такая. Вешаешь обработчик на ресайз:

    window.addEventListener('resize', resizeHandlerSlider);


    Сравниваешь переменную clientWidth при вызове хэндлера и дестроишь свой слайдер.

    const slider = document.querySelector('#slider');
    let { clientWidth } = document.body;
    let yourSlider;
    
    const sliderInit = () => {
        yourSlider = new Swiper(slider, {...})
    }
    
    const resizeHandlerSlider = () => {
        if (clientWidth !== document.body.clientWidth) {
            clientWidth = document.body.clientWidth;
    
            if (yourSlider) {
                yourSlider.destroy();
            }
    
            sliderInit();
        }
    }
    Ответ написан
    1 комментарий
  • Что значит оборачивание функции в скобки (function() { ... })?

    copist
    @copist
    Empower people to give
    Короткий ответ
    (function() { ... })()
    Это определение анонимной функции без параметров и непосредственный вызов её, так же, без параметров

    Длинный ответ
    Зачем оборачивать значение в круглые скобки?

    Оборачивание функции в скобки, так же как и оборачивание константы в скобки - это просто способ показать интерпретатору, что это значение внутри скобок может быть использовано как возвращаемое значение.
    var var_a = 5
    (var_a) /* или */ (5) // не является ошибкой, возвращает значение переменной или выражения
    function func_b() { }
    (func_b) /* или */ (function func_b() { }) // не является ошибкой, возвращает ссылку на функцию
    var var_c = { key: "val" }
    (var_c) /* или */ ({ key: "val" }) // не является ошибкой, возвращает объект
    var var_d = [ "one", "two" ]
    (var_d) /* или */ ([ "one", "two" ]) // не является ошибкой, возвращает массив


    Ну а раз (func_b) - это ссылка на функцию func_b, то значит её можно сразу же вызвать.
    A если (var_c) - это объект, то значит можно сразу же использовать его
    Аналогично (var_d) - это массив, то значит можно сразу же использовать его

    (func_b)() или (function func_b() { })() вызвать функцию
    (var_c).key или ({ "key": "val" }).key использовать объект
    (var_d)[0] или ([ "one", "two" ])[0] использовать массив

    Синтаксической ошибкой было бы использование функции, массива, объекта без скобок ( )
    function func_b() { }() ошибка "Unexpected token )"

    Хотя нет ошибки, по крайней мере в Google Chrome
    { key: "val" }["key"]
    ["one", "two"][0]

    Для чего вообще придумали самовызывающиеся функции?
    Для того, чтобы изолировать переменные и функции, чтобы они не попадали в глобальную область видимости.

    Сравни
    var a = "test"
    alert(a)

    по завершении этого блока переменная a болтается в глобальной области видимости

    и
    (function(){
        var a = "test"
    })()
    
    alert(a) // недоступно, потому что она была локальной переменной внутри анонимной функции


    Почему скобки ( ) пустые?
    В данном случае у функции function() { ... }нет формальных параметров, значит и вызывать можно без параметров.

    Но вообще в самовызывающуюся функцию можно передавать параметры. Это общая практика передачи ссылок на глобальные объекты:

    (function (w, d, $) {
       // некоторым нравится сокращать код путём использования коротких имён переменных
       w['fizz'] = "buzz" // вот так можно принудительно зарегистрировать
                           // глобальную переменную fizz
       $('body').css({background: 'red'}) // вот так можно работать с jQuery через привычную $
                           // даже если библиотека была загружена в режиме noСonflict
    }(window, document, jQuery))


    Некоторым не нравится длинный вариант проверки на undefined и они специально предусматривают лишний параметр, который не инициализируют

    (function (message1, message2, empty) {
        // это и есть проверка на undefined
        if (message1 === empty)
            alert('message1 is undefined')
        else
            alert('message1 = ' + message1)
    
        if (message2 === empty)
            alert('message2 is undefined')
        else
            alert('message2 = ' + message2)
    })("test") // вызвана только с одним параметром, значит второй по имени message2
    //  будет пустой, а третий empty специально ввели в качестве образца
    //  данных с типом "undefined", для служебного использования

    Зачем функция анонимная?
    Аналогично - чтобы не регистрировать её имя в глобальной области видимости, если она нужна один раз.
    Ответ написан
    7 комментариев
  • В чем отличие между git push -u origin master и git push origin master? Зачем ключ -u для команды git push?

    EXL
    @EXL
    Энтузиаст
    В том случае, если ветка master (или branch_name) не является отслеживаемой веткой origin/master (или origin/branch_name), а вы хотите сделать её таковой.

    Выполнив команду git push -u origin master вы устанавливаете связь между той веткой, в которой вы находитесь и веткой master на удалённом сервере. Команду требуется выполнить единожды, чтобы потом можно было отправлять/принимать изменения лишь выполняя git push из ветки без указания всяких алиасов для сервера и удалённых веток. Это сделано для удобства.
    Ответ написан
    2 комментария
  • Windows. Как в VS code изменить "\" на "/" при копировании и вставке относительного пути к файлу?

    @nbo1995
    Нужно скачать плагин Copy Relative Path и в дальнейшем копировать через Copy Relative Pat

    ссылка на источник https://marketplace.visualstudio.com/items?itemNam...
    Ответ написан
    3 комментария
  • Как скрыть msorder на странице msGetOrder?

    @Shwaber
    Тоже столкнулся с данной проблемой и не нашел решение на просторах интернета.
    Удалось решить проблему с помощью сниппета.
    $mainPage = $modx->makeUrl(1);
    $resource = $modx->resource;
    $orderPage = $modx->makeUrl($resource->get('id')) . $get;
    switch ($step) {
        case "clear":
            setcookie ("myOrder", "");
            break;
        case "check":
            if(!isset($_COOKIE["myOrder"])){
                setcookie ("myOrder", $value);
                $modx->sendRedirect($orderPage,array('responseCode' => 'HTTP/1.1 301 Moved Permanently'));
            }
            if($_COOKIE["myOrder"] != $value){
                $modx->sendRedirect($mainPage,array('responseCode' => 'HTTP/1.1 301 Moved Permanently'));
            }
            break;
    }

    Вставил в tpl msOrder (с режимом "clear") и в tpl msGetOrder (с режимом "check").
    &step - режим работы
    &value - что писать в cookie / с чем сравнивать (генерируем маску с использованием данных заказа, например, {$order.id}{$order.num}%{$order.cost})
    &get - GET параметр заказа (?msorder={$order.id})

    Логика работы:
    1. На странице оформления заказа чистим печеньки myOrder.
    2. На странице благодарности проверяем нет ли чего в печеньках. Если печеньки myOrder пусты, то записываем в них наше секретное значение. Если не пусты - сравниваем и либо оставляем пользователя на странице, либо перенаправляем на главную.

    Может решение и костыльное, но самое главное, что работает. Другое в голову пока не пришло.
    Ответ написан
    Комментировать
  • Как скрыть msorder на странице msGetOrder?

    ig0r74
    @ig0r74
    MODX-разработчик
    Посмотреть, что заказывали другие не получится. Попробуйте открыть в режиме инкогнито.
    Ответ написан
    4 комментария
  • Как привязать footer к низу экрана в Twitter Bootstrap?

    @beckson
    Yii2 miggle
    Для Bootstrap4:
    <body class="d-flex flex-column min-vh-100">
        <div class="wrapper flex-grow-1"></div>
        <footer></footer>
    </body>
    Ответ написан
    2 комментария
  • VueJS + PHP. Как это всё подружить?

    @marsdenden
    vue-router сам по себе, роутер на php - сам по себе, никак между собой не связаны. Если от бэкенда нужны только данные и никакого дополнительного функционала, я бы попробовал сделать сервер на ноде, благо модули готовые есть, по крайней мере писать на одном языке проще и эффективнее, чем на двух (имхо). А так все просто - фронт использует axios, в который передается url, параметры и callback для обработки ответа. Бэк обрабатывает вызов и отправляет JSON с данными и на этом его миссия закончилась, фронт в колбэке получает json и делает свое дело.
    Например, как я это сделал (метод - всегда POST)

    в App.vue в methods
    callApi(url,prms,callback){
      this.setServerError('',''); // это функция, которая в data выставляет определенные поля
      //в результате чего ошибки выводятся прямо на странице, удобно для отладки
      axios({
        method:"post",
        url:url,
        data:prms
      }).then((response) => {
        // в response.data получаем JSON, 
        // в моем случае сервер формирует обязательные поля success,error,buffer
        // в buffer  перед выдачей JSON снимается html-вывод, возможно это отладочная информация,
        // которую выдает backend, возможно PHP-warnings
        let dt=response.data;
        if(!dt.success){
           	this.setServerError(dt.error,dt.buffer);
        }else{
            // ну и, собственно, сам вызов колбека, который происходит только в случае успешного приема данных
            callback(dt);
        }
      }).catch((error) => {
        // эту часть вызывает сам axios при возникновении серверных ошибок, то есть все, что не 200 OK 
        // позволяет увидеть, в частности, ошибку 500, вернее сам факт ее возникновения, если она обрабатывается
        // "стандартным" методом апача - пустая страница и все
        this.setServerError(error.message,error.stack);
      });
    },



    далее в created создается подписка, можно использовать Bus.js, у меня по другому

    this.$root.$on('callApi',(url,prms,callback)=>{this.callApi(url,prms,callback)});


    ну и в компоненте или где еще в проекте делается вызов

    this.$root.$emit('callApi', '/api/goods', {action: 'getgoodsinfo', article: '12345678'}, (dt) => {
             this.articleinfo=dt.data.articleinfo;
          })


    на бэкэнде, соответственно, есть api.php, в котором происходит разбор url, чтение параметров и формирование результата

    заготовка api.php
    <?php
    // регистрируем функцию завершения, чтобы обрабатывать грубые ошибки, 
    //например вызов несуществующего метода у объекта
    register_shutdown_function(function () {
        $error = error_get_last();
        if ($error && ($error['type'] == E_ERROR || $error['type'] == E_PARSE || $error['type'] == E_COMPILE_ERROR)) {
            $res=array(
                'buffer'=>ob_get_contents(),
                'success'=>false,
                'error'=>"PHP Fatal: ".$error['message']." in ".preg_replace('/(.*)\/(.*)/', "$2", $error['file']).":".$error['line']
            );
            ob_clean();
            header('HTTP/1.1 200 Ok');
            header("Access-Control-Allow-Origin: *");
            echo json_encode($res);
            // ... завершаемая корректно ....
        }
    });
    
    // для кроссдоменного CORS, при необходимости - закомментировать или заменить звездочку на требуемое
    if($_SERVER['REQUEST_METHOD']=='OPTIONS' ){
        ob_clean();
        header("Access-Control-Allow-Origin: *");
        header("Content-type: application/json; charset=utf-8");
        header("Access-Control-Allow-Headers: X-Requested-With, Content-Type");
        header("Access-Control-Request-Method: POST");
        return true;
    }
    
    // /*
    // протокол обмена
    // - вход - команда по сегменту, например http://site.ru/api/goods - api - попали сюда, goods - команда REST
    // в php://input должен быть json, в котором обязателен параметр action, например getgoodsinfo
    // в результате формируется имя функции класса goods_getgoodsinfo, которая вызывается 
    // с параметром входящего json
    
    // функция класса должна вернуть массив с тремя полями - data & success & error
    // в поле data возвращается непосредственно результат функции, в нашем случае - реестр чеков
    // в поле success возвращается true | false - признак успешного выполнения
    // в поле error возвращается описание ошибки в случае неудачного выполнения функции
    // */
    
    $api=new ApiCls();
    
    // функция, проверяющая залогиненность юзера
    if(is_user_login()){ 
        $api->checkcommand();
    }else{
        $res=array('succes'=>false,'error'=>'Пользователь не авторизован','data'=>'');
        ob_clean();
        header("Content-type: application/json; charset=utf-8");
        header("Access-Control-Allow-Origin: *");
        header("Access-Control-Allow-Headers: X-Requested-With, Content-Type");
        echo json_encode($res);
    }
    
    return true;
    
    class ApiCls{
        function checkcommand(){ // точка входа для класса api, здесь первичный разбор, 
            //вызов метода и возврат результата
            // главное - определить второй сегмент в url, то есть в случае http://site.ru/api/goods
            $segment=????????; // в $segment должен оказаться 'goods'
    
            $res=array('success'=>false,'error'=>'Empty action'); // сразу проверка на наличие action в параметрах
            if(!$segment){
                $res['error']='Empty command';
            }else{
                if($_SERVER['REQUEST_METHOD']=='PUT' || $_SERVER['REQUEST_METHOD']=='POST'){
                    $reqdata = file_get_contents('php://input'); 
                    $b=json_decode($reqdata);
                    $b=get_object_vars($b);
                    if(isset($b['action'])){
                        $res['error']='no error';
                        $nm=$segment.'_'.$b['action'];
                        $r=$this->$nm($b); // вызов метода по action из пост и дальнейшая обработка результатов
                        // чё-то тут намутил, но работает - и ладно
                        if(!isset($r['success'])){
                            $res['success']=false;
                            $res['error']='No success flag in method '.$nm;
                        }else{
                            if(!isset($r['data'])){
                                $res['success']=false;
                                $res['error']='No result data in method '.$nm;
                            }else{
                                $res['success']=$r['success'];
                                $res['data']=$r['data'];
                                if(!$r['success']){
                                    if(isset($r['error'])){
                                        $res['error']=$r['error'];
                                    }else{
                                        $res['error']='Success is false, but no error message in method '.$nm;
                                    }
                                }
                            }
                        }
                    }
                }
            }
            // непосредственная выдача данных
            $this->_printresponse($res);
        }
        function _printresponse($res){
            // проверяем наличие html-вывода (отладка или warnings)
            $res['buffer']=ob_get_contents();
            if($res['buffer']!=''){
                $res['success']=false;
                isset($res['error'])?$res['error']=implode(',',array('module error',$res['error'])):$res['error']='module error';
            }
            // очищаем буфер вывода и формируем свои заголовки
            ob_clean();
            header("Content-type: application/json; charset=utf-8");
            header("Access-Control-Allow-Origin: *");
            header("Access-Control-Allow-Headers: X-Requested-With, Content-Type");
            // ну и, наконец, выдаем результирующий JSON
            echo json_encode($res);
        }
        function __call($name,$post){
            // эта функция вызывается при попытке вызвать несуществующий метод класса, то есть при вызове '/api/blablabla' получим отлуп
            $info=array('method'=>$name,'post'=>$post,'error'=>'Method not found','success'=>false);
            return $info;
        }
        /*********************************************************/
        // начинаем блок методов api
        function goods_getgoodsinfo($prm){
            // формируем заготовку ответа
            $res=array('data'=>array(),'success'=>true,'error'=>'');
            // при необходимости здесь можно вставить проверку наличия полномочий у пользователя
            // и если что не так, то выключить success, прописать "облом!" в error и не возвращать данные
            $res['data']['articleinfo']= getArticleInfo($prm['article']); // вызов функции, 
            //которая собирает требуемые данные для определенного артикула и возвращает, опять же
            // в формате JSON
            return $res;
        }
    }
    ?>



    Вот как-то так... Дальше только вопрос - как прикрутить этот api.php к сайту и вопросы безопасности, но это уже другая тема
    Ответ написан
    1 комментарий
  • Фильтр JSON данных?

    In4in
    @In4in
    °•× JavaScript Developer ^_^ ו°
    var newJson = json.filter(function(e){
       return e.attributes.attribute_pa_color == "navy";
    });
    Ответ написан
    Комментировать
  • Одновременное использование hover и before или другое решение проблемы?

    webvany
    @webvany Автор вопроса
    Дизайнер
    Проблема решилась самым простым образом.
    Сначала нужно писать псевдокласс :hover, а затем псевдоэлемент :before, таким образом:
    div:hover:after{}
    Ответ написан
    2 комментария
  • Как решить проблему с запуском gulp?

    @game802
    Судя по ошибке Error: Cannot find module 'gulp-sass' у Вас не хватает пакета для запуска gulp'a.
    Попробуйте установить необходимый пакет следующей командой: npm i gulp-sass --save-dev
    И Вы лезете куда-то совсем далеко за решением данной проблемы.
    1) Попробуйте добавить node-sass в package.json, в devDependencies:
    "node-sass": "4.7.2"
    2) Полностью удалить папку node_modules
    3) Заново установить зависимости из package.json командой npm i
    Ответ написан
    1 комментарий
  • Как определить нажатую кнопку по событию submit?

    @eskanderdon
    Знаю, знаю.. сто лет в обед.. но может быть какой-нибудь сёрфер оценит (не знаю)...

    <script type="text/javascript">
    $(function () {
       var target = null;
        $(':input').focus(function() {
          target = $(this).val();
        });
        // НЕ ПЕРЕНОСИТЕ ЭТОТ ФРАГМЕНТ В SUBMIT
     
      $('form').submit( function () {
        
        if ( target == 'save' ) {
          alert('[Save] is pressed')
        } else if ( target == 'delete' ){
          alert('[Delete] is pressed')
        } else {
          alert('{unknown button is pressed}')
        }
         return false;
      });
    });
    </script>
    
    <form action="" method="post">
      <button type="submit" value="save" name="action">Сохранить</button>
      <button type="submit" value="delete" name="action">Удалить</button>
    </form>
    Ответ написан
    2 комментария
  • Как сделать при прокрутке, автоматический подгружались другие страницы?

    @ART4 Автор вопроса
    Разобрался
    <div id="pdopage">
        <div class="rows">
            [[!pdoPage?
                 &elementClass=`modSnippet`
                 &element=`pdoResources` 
                 &tpl=`newscategoryTpl`
                 &includeContent=`1`
                 &includeTVs=`image`
                 &processTVs=`1`
                 &hideContainers=`1` 
                 &sortby=`menuindex`
                 &sortdir=`ASC`
                 &showHidden=`1`
                 &parents=`4`
                 &depth=`1`
                 &ajaxMode=`scroll`
                 &limit=`5`
            ]]
        </div>
       [[!+page.nav]]
    
    </div>
    Ответ написан
    Комментировать
  • Как в MODX REVO в админке скрыть поле содержимого сесурса?

    qork
    @qork
    { background: #F00B42 }
    В разделе "Настройка форм" создаешь активный профиль. Для профиля задаешь с указанием шаблона два набора правил - для редактируемых ресурсов и для новых ресурсов. В каждом наборе правил снимаешь галку с "modx-resource-content".
    Ответ написан
    2 комментария
  • Полная загрузка страницы jQuery?

    Mr_Sergo
    @Mr_Sergo
    <script type='text/javascript' src='http://code.jquery.com/jquery-1.10.1.min.js'></script>
    	<script type='text/javascript'>
    		$(window).on('load', function () {
    			$('#wrap_preloader').delay(500).fadeToggle(500);
    		});
    	</script>


    <div id='wrap_preloader'>
    		Идет загрузка...
    	</div>


    #wrap_preloader {
    		width: 100%;
    		height: 100%;
    		position: fixed;
    		margin: 0px auto;
    		background: #282828;
    		z-index: 9999;
    		text-align: center;
    		color: #fff;
    		letter-spacing: 5px;
    		font-family: arial;
    		font-size: 50px;
    		padding-top: 260px;
    	}


    Ответ написан уже давно но тем не менее. Скачал утилиту для изменения скорости интернета, попробовал поставить 50кб/сек.- сначала долго висит ПРЕЛОАДЕР, после полной загрузки страницы пропадает. Поставил 1000кб/сек.- прелоадер пропадает почти сразу. Работает прелоадер, вообщем, четко, как и должен. Может кому пригодится.
    Ответ написан
    Комментировать
  • Полная загрузка страницы jQuery?

    webirus
    @webirus
    Тыжверстальщик! Наверстай мне упущенное...
    От сердца отрываю. Прелоадер нужно поместить сразу после открывающего body, чтобы не проскакивали незагруженные части страницы перед показом прелоадера.
    Всё в одном блоке, чтобы удобней было ставить и удалять его при необходимости и стили, скрипты работали более корректно.
    <!-- preloader -->
        <style type="text/css">
            .preloader_bg { position: fixed; background: rgba(15,15,15,1); width: 100%; height: 100%; top: 0; left: 0; z-index: 200; }
            .preloader_content { position: fixed; left: 50%; top: 50%; transform: translate(-50%,-50%); z-index: 201; font-size: 14px; }
            .preloader_content span { display: block; margin: auto; text-align: center; text-transform: uppercase; color: rgba(225,225,225,1);}
        </style>
        <script type="text/javascript">
        $(function(){
            $('.preloader_bg, .preloader_content').fadeIn(0);
            $(window).load(function(){
                $('.preloader_bg').delay(250).fadeOut(1500);
                $('.preloader_content').delay(250).fadeOut(750);
            });
        });
        </script>
        <div class="preloader_bg"></div>
        <div class="preloader_content">
            <span>Идет загрузка...<br>Подождите...</span>
        </div>
        <noscript>
            <style>
                html, body { opacity: 1 !important; }
                .preloader_bg, .preloader_content { display: none !important; }
            </style>
        </noscript>
        <!-- /preloader -->
    Ответ написан
    4 комментария
  • Как использовать normilize с gulp?

    @LMI
    1. Если у тебя уже установлен Gulp и настроен локально в папке проекта, то в консоли переходишь в папку этого своего проекта и вводишь npm install node-normalize-scss --save-dev

    2. Потом в основном sass-файле делаешь импорт @import "normalize";

    3. В таске по компиляции sass в css в пайп добавляешь строчку кода
    includePaths: require('node-normalize-scss').includePaths


    Вот полный код и документация

    var gulp = require('gulp');
    var sass = require('gulp-sass');
     
    gulp.task('sass', function () {
      gulp.src('path/to/input.scss')
        .pipe(sass({
          // includePaths: require('node-normalize-scss').with('other/path', 'another/path') 
          // - or - 
          includePaths: require('node-normalize-scss').includePaths
        }))
        .pipe(gulp.dest('path/to/output.css'));
    });


    https://www.npmjs.com/package/node-normalize-scss
    Ответ написан
    1 комментарий
  • Почему не удается запустить gulp сборку проекта на другом компьютере?

    Вы выполнили команду:
    npm install -g gulp --save-dev

    Флаг -g означает глобальную установку в системе.
    Сомневаюсь, что в данном случае можно использовать --save-dev

    Советуется использовать gulp-cli, т.к. разные проекты могут использовать разные версии gulp'а.
    Допустим если один проект использует gulp 3.9, а другой 4, то будут проблемы с использованием глобального gulp'а.

    Поэтому давайте поставим gulp-cli глобально:
    npm install -g gulp-cli
    Потом выполните, чтобы убедиться, что gulp-cli успешно установился.
    gulp -v
    [14:08:42] CLI version 2.0.1

    Далее в папке с package.json выполните команду, чтобы установить пакеты необходимые для выполнения gulpfile'а
    npm install

    Запустить выполнение default'ного task'а можно командой: gulp, не обязательно указывать default
    Ответ написан
    1 комментарий