Магнитная коммерция: создание креативного веб-сайта Dash | Кодропс

Магнитная коммерция: создание креативного веб-сайта Dash | Кодропс



Ребрендинг был запланирован на некоторое время. Мы хотели чего-то, что помогло бы нам выделиться. Не просто выглядеть по-другому, но и владеть тем, что мы на самом деле делаем.

Этот процесс привел к простой концепции: магнитной коммерции. Отличный цифровой опыт не просто информирует. Они привлекают людей. Эта идея сформировала наш новый логотип, в котором часть буквы D втянута внутрь, словно магнитной силой. Эмблема стала отправной точкой практически для всех последующих дизайнерских решений.

Как только мы представили этот ресурс как вращающийся 3D-объект, взаимодействие с курсором стало естественным. Логотип должен вести себя так же, как и его концепция. Наведите на него курсор, и он потянет. Эта одна деталь задала тон тому, как мы будем думать о движении в остальной части сайта.

Другое раннее решение заключалось в том, чтобы позволить дизайну iOS определять, как мы обрабатываем карточки и призывы к действию. Мы разработали карточки проектов как преднамеренный намек на уведомления iOS: знакомые, тактильные и немного неожиданные по контексту. Правила бренда были строгими. Это ограничение оказалось полезным. Это остановило принятие решений и подтолкнуло нас к чему-то более продуманному.

В общей сложности проект длился несколько месяцев. Идея пришла в голову относительно быстро. Правильное содержание и правильная доработка анимации в процессе разработки — вот на что ушло время.

Фигма для дизайна. Руководящие принципы бренда были четко определены, и Figma сохраняла все систематизированным (тип, интервалы, компоненты), не мешая итерациям.

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

ГСАП для тех частей, которые не удалось достичь собственным взаимодействиям Webflow, особенно для более точного поведения, управляемого курсором, и последовательности.

Пользовательский WebGL для фона героя. Этот человек не мог жить больше нигде.

Предыстория героя: искажение живой поверхности

Фон героя начался с простой идеи: использовать полноэкранное видео в качестве текстуры и искажать его в ответ на движение курсора. Целью было сделать фон отзывчивым, но не отвлекающим.

Одна вещь была важна с самого начала. Мы не хотели, чтобы эффект вел себя как простая рябь вокруг курсора. Вместо этого искажение должно продолжаться в направлении движения, создавая впечатление, что поверхность притягивается, а не просто реагирует на состояние наведения.

Подход

Эффект полностью реализован во фрагментном шейдере. Вместо наложения эффектов на видео шейдер напрямую переназначает координаты текстуры видео. Курсор определяет область влияния, а направление движения управляет распространением искажения. Затухающая синусоидальная функция генерирует волну, которая вызывает смещение.

Настраиваемые значения определяются один раз и передаются в средство визуализации:

const SETTINGS = {
  radius: 0.41,
  amplitude: 0.082,
  frequency: 13,
  speed: 0.98,
  carry: 6,
  stagger: 12,
  centerPower: 2,
  verticalDampPower: 2.2,
  motionGain: 220,
  speedDecay: 0.86,
};

Геометрия состоит из одного полноэкранного квадрата:

const vertices = new Float32Array([
  -1, -1, 0, 0,
   1, -1, 1, 0,
  -1,  1, 0, 1,
  -1,  1, 0, 1,
   1, -1, 1, 0,
   1,  1, 1, 1,
]);

Само искажение происходит во фрагментном шейдере:

float maskFn(vec2 uv) {
  vec2 d = uv - uMouseSm;
  d.x *= uAspect;
  float dist = length(d);
  return pow(smoothstep(uRadius, uRadius - uSoft, dist), uCenterPow);
}

float wave = sin(
  d.y * uFreq +
  dot(d, dir) * uCarry +
  uTime * uSpeed +
  d.y * uStagger
);

d += dir * (wave * amp * maskFn(uv) * damp);

В результате получается эффект, который реагирует на движение курсора, не ведя себя как простое взаимодействие при наведении. Искажение несет импульс в направлении движения, прежде чем постепенно стабилизироваться.

Направление движения и постоянство

Прежде чем значения передаются в шейдер, состояние взаимодействия сглаживается и разрушается на стороне JavaScript:

motionTarget *= SETTINGS.speedDecay;
const mappedMotion = Math.min(motionTarget * SETTINGS.motionGain, 1);

motion += (mappedMotion - motion) * SETTINGS.momentum;
dirSm.x += (dirTarget.x - dirSm.x) * SETTINGS.dirSmooth;
dirSm.y += (dirTarget.y - dirSm.y) * SETTINGS.dirSmooth;

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

Визуальная сдержанность

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

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

В остальном герой намеренно прост: черный фон, видео без полей и шейдер, примененный непосредственно к текстуре. Сведение всего остального к минимуму помогает сосредоточиться на самом взаимодействии.

Архитектура

Структура довольно проста.

Установка состоит из контейнера героя, скрытого видеоэлемента, используемого в качестве источника текстуры, и холста WebGL, расположенного над ним.

Отсюда рендерер выполняет пять основных задач:

  1. Подготовьте источник видео и дождитесь воспроизведения.
  2. Инициализируйте средство рендеринга WebGL и скомпилируйте шейдеры.
  3. Отслеживайте движение указателя и сглаживайте состояние взаимодействия.
  4. Загружайте текущий видеокадр в графический процессор каждый кадр.
  5. Рендеринг одного полноэкранного прохода.

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

Загрузка кадров осуществляется только после того, как видео готово:

if (video.readyState >= 2) {
  gl.texImage2D(gl.TEXTURE_2D, 0, gl.RGBA, gl.RGBA, gl.UNSIGNED_BYTE, video);
}

rafId = requestAnimationFrame(renderFrame);

Реализация делает цикл рендеринга легким. Значения взаимодействия сглаживаются с течением времени, шейдер переназначает только UV-координаты, холст ограничивается главным разделом, а рендеринг не начинается, пока видео не будет готово.

Тот же подход можно повторно использовать с разными источниками видео, профилями искажений или разделами сайта без изменения общей структуры.

Размышления

Конечный результат намного ближе к тому, что мы хотели передать на сайте. Техническая реализация возникла сравнительно быстро. Большая часть времени была потрачена на доработку движения, редактирование контента и обеспечение того, чтобы все это работало вместе.

Одной из самых больших проблем было понять, когда прекратить добавление. Небольшие корректировки тайминга, замедления и копирования часто оказывали большее влияние, чем введение новых эффектов.

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

В целом проект укрепил идею, которая с самого начала сформировала ребрендинг: взаимодействие работает лучше всего, когда оно поддерживает концепцию, а не привлекает внимание к себе.



Источник

Оставьте комментарий

Ваш адрес email не будет опубликован. Обязательные поля помечены *

Прокрутить вверх