Задать вопрос
  • Как сделать простое настольное приложение на JavaScript?

    Xuxicheta
    @Xuxicheta
    инженер

    Желательно конечно чтобы его можно было с минимальными усилиями потом перенести в веб.


    Делаешь обычный сайт на чем угодно, оформляешь к нему манифест PWA и можно устанавливать как обычное приложение на десктоп. Оно закеширует скрипты в сервис-воркере и не надо будет каждый раз скачивать.
    Electron не нужен.

    Вот например официальный сайт Angular удовлетворяет требованиям PWA и может быть инсталлирован
    5def8b9db9bbc873815458.png
    Ответ написан
    Комментировать
  • Как связать front-end на Angular и back-end asp.net core?

    Xuxicheta
    @Xuxicheta Куратор тега Angular
    инженер
    МС конкретно намутила воду пытаясь в свой фреймворк адаптировать для SPA.
    Мыслите по другому.
    Если вам нужно веб-приложение, веб-приложение состоит из двух частей (как минимум) - фронт и бэк.
    Фронт это гора скриптов, которые пользователь получает от статик веб-сервера. Бэк - логика, которая умеет общаться с бд и отвечает по протоколу, доступному для фронта.
    Поскольку asp.net это такая крупная энтерпрайз штука, то и фреймворк для фронта МС выбрали крупный, энтерпрайзный - Ангуляр и попытались интегрироватся с ним как могли. (Странно что МС не нашла очередной фатальный недостаток и не взялась пилить собственный веб-фрейм)
    Спасибо им конечно, но по факту это два разных относительно незавимых приложения все равно и в доке Ангуляра вы про asp.net не найдете ничего.

    И возвращаясь к сути вопроса, да, фронт делает http запросы на бэк. Асинхронные запросы в обе стороны тоже возможны, через websocket.
    Ответ написан
  • Как перехватывать все ошибки в приложении, если некоторые функции уже обернуты в try ... catch?

    Xuxicheta
    @Xuxicheta
    инженер
    Правильный ответ - не нужно все ошибки обрабатывать в одном месте.
    А вообще если нужна промежуточная обработка ошибок, делают проброс ошибки дальше
    function mayBeError() {
      try {
        throw new Error('iiii')
      } catch (e) {
        console.error('error in mayBeError');
        throw e;
      }
    }

    Функции должны выкидывать свои ошибки вовне, это нормально.

    Централизованного способа нет и было бы странно если бы он был, иногда исключений просто куча. Их могут в логике использовать.

    Можно только неперехваченные ошибки ловить, через
    для браузера событие error
    window.onerror = function (message, file, line, col, error) {
       console.warn("Error occurred: " + error.message);
       return false;
    };

    и для ноды событие uncaughtException
    https://nodejs.org/api/process.html#process_event_...
    Ответ написан
    Комментировать
  • Как выполнить скрытие и показ одновременно?

    Xuxicheta
    @Xuxicheta
    инженер
    Оно и происходит одновременно, но у вас max-height: 1000px; transition: max-height 1s;
    Когда вы делает клик, максимальная высота одного начинает увеличиваться с 0 до 1000, а у друго уменьшаться с 1000 до 0. В течении секунды аж.
    У которого от 0 до 1000 max-height быстро вырастет на достаточную величину чтобы показать элемент, а когда с тысячи едет, элемент пропадает из виду почти в самом конце анимации.

    Решение - уменьшить время анимации и уменьшить высоту.
    Ответ написан
  • Ре-рендер элемента HTML на JS?

    Xuxicheta
    @Xuxicheta
    инженер
    "перерисовать" это что? Перерисовывать можно по разному, точечно вносить изменения например.
    Содержимое элемента можно сменить полностью задав innerHTML.
    Можно создавать ноды, удалять существующие и на их место вставлять созданные.
    Можно, как это делают некоторые движки, создавать параллельную структуру, а потом пробегаться и искать изменения относительно реальной, и если они найдены менять реальную.
    Ответ написан
    2 комментария
  • Работа с прототипами, как можно сделать лучше?

    Xuxicheta
    @Xuxicheta
    инженер
    Сделать лучше очень просто - не надо так делать. Расширять стандартные объекты плохо, потом сами забудете где какие изменения.
    Используйте обычное
    const revStr = str => str.split("").reverse().join("");

    При вызове занимает практически столько же места и всегда можно отследить откуда она взялась и никаких потенциальных конфликтов.
    Да и что касается геттеров, лучше ими не злоупотреблять.
    Ответ написан
  • Как раскрыть всю ветку дерева в mat-tree?

    Xuxicheta
    @Xuxicheta Куратор тега Angular
    инженер
    это же плоское дерево. Просто берешь ноду, раскрываешь и двигаешься назад по массиву раскрывая ноды до тех пор пока не доберешься до level 0

    вот
    https://stackblitz.com/edit/angular-yi9tbm-i9tl2k

    или даже так
    private expandAcsendants(index: number) {
      for (let c = index; this.treeControl.dataNodes[c]; c--) {
        this.treeControl.expand(this.treeControl.dataNodes[c]);
        if (this.treeControl.dataNodes[c].level === 0) {
          break;
        }
      }
    }
    Ответ написан
    Комментировать
  • Как как отправить данные авторизации в приложение на другом порту на NestJs через websockets?

    Xuxicheta
    @Xuxicheta
    инженер
    И есть клиентское приложение на 3001 порту

    а потом пишете
    @WebSocketGateway(3000, {transports: ['websocket']})


    Так на 3001 или 3000?
    Ответ написан
  • Объясните как работает кросдоменная политика безопасности на примере модуля на Angular?

    Xuxicheta
    @Xuxicheta Куратор тега Angular
    инженер

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

    это какие? Если речь про WebSocketSubject, то это таки rxjs, а не Ангуляр, и да, можно юзать, почему нет.
    Ангуляр же про вебсокеты ничего не знает.

    Почему тогда сейчас я могу работать с данным апи из любого другого места средствами ангуляра?

    Ангуляр тут вообще не при делах. Браузер делает запрос. Если запрос идет на другой домен, браузер сначала спрашивает разрешение у этого домена, можно ли ему сделать этот запрос. Посредством другого запроса с методом OPTIONS. Так называемый префлайт.
    Если бэкенд на том домене отдает заголовки в которых указано "ок, можно", то браузер запрашивает данные и все ок.
    Это есть Cross-origin resource sharing, CORS
    Таким образом успешность вашего запроса целиком зависит от бэкенда.
    почитать

    Плюс еще с сайтов на схеме https нельзя делать нешифрованные запросы, можно только https и wss.
    Ответ написан
  • Задание с learn.javascript. Поясните код?

    Xuxicheta
    @Xuxicheta
    инженер
    + Чтобы число получить и работало строгое равенство number === 0
    Унарный плюс
    https://learn.javascript.ru/operators#preobrazovan...
    А обратных слешей у тебя в вопросе вообще нет, но вообще они используются для экранирования или указания спецсимволов
    Ответ написан
    Комментировать
  • Какой проект сделать чтоб показать силу в JavaScript?

    Xuxicheta
    @Xuxicheta
    инженер
    Написать свой компонентный фреймворк
    Ответ написан
    Комментировать
  • Использование Linux для различных яп?

    Xuxicheta
    @Xuxicheta
    инженер
    В большинстве популярных дистрибутивов Linux python идет уже сразу из коробки.
    Ответ написан
    Комментировать
  • Как изменить netbeans.conf в ubuntu 18.04 если пишет, что файл только для чтения?

    Xuxicheta
    @Xuxicheta
    инженер
    Local: To make individual changes that will apply only to a specific user, put them into the etc/netbeans.conf file in the user's userdir .

    ${userdir}/etc/netbeans.conf

    The local file does not exist by default! If you don't see a ${userdir}/etc directory you have to create the file yourself. The easiest way to do that is to copy the global netbeans.conf file from the NetBeans installation folder to the local ${userdir}/etc folder, and then make the desired changes.
    Ответ написан
    1 комментарий
  • Как отключить звук на всей странице в React?

    Xuxicheta
    @Xuxicheta
    инженер
    new Audio() создает HTMLAudioElement.
    Вместо того чтобы создавать его каждый раз, его можно создать один раз или даже вставить в разметку, а из события дергать только play
    Чтобы заткнуть проигрыватель, ему нужно выставить свойство muted в true. Вы же тут даже ссылки на него не оставляете, поэтому свойство ставить некуда.

    А уж как это сделать глобально вам решать, можно через стор типа redux.

    И кстати непонятно что вам мешало сделать просто
    onMouseOver={() => settings.isSound && new Audio('/sound/menuhover.wav').play()}
    Ответ написан
    1 комментарий
  • Как прервать выполнение запроса?

    Xuxicheta
    @Xuxicheta Куратор тега Angular
    инженер
    А в примере входной параметр [minTermLength]="2" вам ни о чем не говорит?
    и уберите промис, кошмар же
    Ответ написан
  • Верно ли я понял?

    Xuxicheta
    @Xuxicheta
    инженер
    нет
    return contacts[i][prop] || "No such contact"
    означает
    if (contacts[i][prop]) {
      return contacts[i][prop];
    } else {
      return "No such contact";
    }

    или
    return contacts[i][prop]
      ? contacts[i][prop]
      : "No such contact"


    Читайте как работает OR, если в выражении первая часть перед || истинна (Truthy) - возвращается она, если ложна (Falsy) - возвращается вторая часть выражения, после ||.

    x === (false || x)
    Ответ написан
    Комментировать
  • Линейное выполнение функций через callback в Node.js?

    Xuxicheta
    @Xuxicheta
    инженер
    Вот так примерно выглядит ваш ответ на коллбэках. Примитивный вариант, без обработок ошибок. Фактически это своя миниреализация Promise.all

    // имитация реквеста
    function getDetailedHistory(itemId, allHomeEvent, done) {
      setTimeout(300, () => done('im getDetailedHistory'));
    }
    
    // имитация реквеста
    function getDetailedHistoryReverse(itemId, allHomeEvent, done) {
      setTimeout(400, () => done('im getDetailedHistoryReverse'));
    }
    
    
    function getHistory(allHomeEvent, callback) {
      // вместо запуска сначала соберем все запросы в массив функций.
      const requests = [];
      for (const event of allHomeEvent) {
        let itemId = event.id
    
        if (event.home.name === "Women") {
          // записываем в массив функцию, замыкающую наш реквест
          requests.push(done => getDetailedHistory(itemId, allHomeEvent, done));
        }
    
        if (event.away.name === "Women") {
        	requests.push(done => getDetailedHistoryReverse(itemId, allHomeEvent, done));
        }
      }
    
      // запомнить число реквестов, чтобы понять когда все закончились, они же асинхронны.
      let counter = requests.length;
     
       // при окончании каждого реквеста, уменьшаем счетчик и смотрим уже конец или еще нет
       const requestDone = () => {
      	counter -= 1;
        if (counter <= 0) {
           // реквесты кончились, пора дергнуть главный коллбэк
        	callback();
        }
      }
      
      // а теперь пора выполнить весь массив
       requests.forEach(request => request(requestDone));
    }
    
    getHistory(allHomeEvent, () => console.log('all done!'));


    Подумайте как вынести выполнялку всех запросов в отдельную функцию, для переиспользования в дальнейшем.
    Чтобы было так
    const requests = getHistory(allHomeEvent);
    doneAll(requests, () => console.log('all done!'));
    Ответ написан
  • Как правильно использовать ngRx?

    Xuxicheta
    @Xuxicheta Куратор тега Angular
    инженер
    Флаг для модалки прокидывается в модалку через DI. Ну по крайней мере в материале. Зачем его в стор?
    Я храню в сторе в основном данные от бэка или общие ui-состояния.
    Ток не в ngrx, это для мазохистов. Акита норм.
    Ответ написан
  • Как сделать, чтобы select отображал options в зависимости от выбранной option соседнего select'а?

    Xuxicheta
    @Xuxicheta Куратор тега Angular
    инженер
    <select #optSelect (change)="kindSelect.kinds = filterConfig[optSelect.value]">
      <option *ngFor="let opt of filterConfig | keyvalue">{{opt.key}}</option>
    </select>
    
    <select #kindSelect>
      <option *ngFor="let kind of (kindSelect.kinds || filterConfig.fruit)">{{kind}}</option>
    </select>


    public filterConfig = {
      fruit: ['apple', 'orange', 'pineapple', 'grape'],
      vegetable: ['carrot', 'potato', 'dill', 'cucumber']
    }

    Промежуточная переменная kindSelect.kinds была введена из-за того, что если просто взять optSelect.value на начальной отрисовке шаблона value еще нет, optSelect.value появляется при первой детекции изменений, и в дев моде на втором проходе детекции обнаруживаются несоответствия значений с шаблоном, что вызовет ExpressionChangedAfterItHasBeenCheckedError.

    Совет: не увлекаться таким шаманством, а сделать нормальную реактивную форму и подписку на нее.
    Ответ написан
    Комментировать