Premium design & development studio, Dubai. Serving global clients since 2018. →

* * FIX v9: * - BLOCK 2: Cards default to position 0 (flush left) on load. * Mouse parallax only activates once the cursor enters the slider. * On mouseleave, cards smoothly return to position 0 (flush left). */ document.addEventListener('DOMContentLoaded', function () { var SLIDE_DUR = 2000; function cssVar(n, fb) { return getComputedStyle(document.documentElement).getPropertyValue(n).trim() || fb; } /* BLOCK 1 — AUTO PROGRESS BAR + IMAGE CYCLING */ document.querySelectorAll('.hero_projects_card').forEach(function (card) { var visual = card.querySelector('.hero_projects_visual'); var images = Array.from(card.querySelectorAll('.hero_projects_image')); var logo = card.querySelector('.hero_projects_logo'); if (!visual || !images.length) return; var old = visual.querySelectorAll('.hero_projects_progress, .n4-progress-bar'); old.forEach(function (el) { el.remove(); }); var bar = document.createElement('div'); bar.className = 'n4-progress-bar'; var fills = []; for (var i = 0; i < images.length; i++) { var seg = document.createElement('div'); seg.className = 'n4-pb-seg'; var fill = document.createElement('div'); fill.className = 'n4-pb-fill'; seg.appendChild(fill); bar.appendChild(seg); fills.push(fill); } visual.insertBefore(bar, visual.firstChild); var cur = 0, timer = null; function showSlide(idx) { images.forEach(function (img, n) { img.style.opacity = n === idx ? '1' : '0'; }); fills.forEach(function (f, n) { f.style.transition = 'none'; f.style.width = n < idx ? '100%' : '0%'; }); requestAnimationFrame(function () { requestAnimationFrame(function () { fills[idx].style.transition = 'width ' + SLIDE_DUR + 'ms linear'; fills[idx].style.width = '100%'; }); }); } function startCycle() { clearTimeout(timer); showSlide(cur); timer = setTimeout(function next() { cur = (cur + 1) % images.length; showSlide(cur); timer = setTimeout(next, SLIDE_DUR); }, SLIDE_DUR); } function stopCycle() { clearTimeout(timer); cur = 0; bar.style.opacity = '0'; if (logo) logo.style.opacity = '1'; images.forEach(function (img) { img.style.opacity = '0'; }); fills.forEach(function (f) { f.style.transition = 'none'; f.style.width = '0%'; }); card.querySelectorAll('video').forEach(function (v) { v.pause(); }); } card.addEventListener('mouseenter', function () { bar.style.opacity = '1'; if (logo) logo.style.opacity = '0'; card.querySelectorAll('video').forEach(function (v) { v.play().catch(function () {}); }); startCycle(); }); card.addEventListener('mouseleave', stopCycle); }); /* BLOCK 2 — DESKTOP MOUSE PARALLAX (> 992px) v9 FIX: - Default position is 0 (cards flush left) — no movement on load. - Parallax only runs while mouse is inside the slider. - On mouseleave, cards snap back to 0 (flush left). - Left edge = 0, right edge = -cachedHidden. Hard clamped. */ (function () { var EDGE_PCT = 0.02; /* 2% inward on each side — set to 0 for flush */ var active = false, ready = false; var cachedHidden = 0, lastListW = 0; var edgeOffset = 0; /* px = list.offsetWidth * EDGE_PCT */ var pendingX = null, rafQueued = false; var cards = [], list = null; window.enableMouseFollow = function () { ready = true; if (window.innerWidth > 992) init(); }; function recache() { if (!list || !cards.length) return; var firstRect = cards[0].getBoundingClientRect(); var lastRect = cards[cards.length - 1].getBoundingClientRect(); cachedHidden = Math.max(0, (lastRect.right - firstRect.left) - list.offsetWidth); edgeOffset = list.offsetWidth * EDGE_PCT; lastListW = list.offsetWidth; } function resetCards() { /* Snap all cards back to natural position (flush left) */ for (var i = 0; i < cards.length; i++) { cards[i].style.transform = 'translateX(0px)'; } pendingX = null; } function applyMove() { rafQueued = false; if (pendingX === null || !list || !active) return; if (list.offsetWidth !== lastListW) recache(); var rect = list.getBoundingClientRect(); /* norm: -1 = far left edge, 0 = centre, +1 = far right edge */ var norm = Math.max(-1, Math.min(1, (pendingX - rect.left - rect.width / 2) / (rect.width / 2) )); /* Full symmetric map: norm -1 -> mv = 0 (first card flush left) norm 0 -> mv = -cachedHidden/2 norm +1 -> mv = -cachedHidden (last card flush right) */ var mv = ((norm + 1) / 2) * (-cachedHidden); /* 2% inward clamp on both sides — same as v8: left stop: -edgeOffset (2% in from first card) right stop: -(cachedHidden - edgeOffset) (2% in from last card) */ if (cachedHidden > edgeOffset * 2) { mv = Math.max(-(cachedHidden - edgeOffset), Math.min(-edgeOffset, mv)); } else { mv = Math.max(-cachedHidden, Math.min(0, mv)); } for (var i = 0; i < cards.length; i++) { cards[i].style.transform = 'translateX(' + mv + 'px)'; } } function init() { list = document.querySelector('[data-hero-slider]'); if (!list) return; cards = Array.from(list.querySelectorAll('[data-hero-card]')); if (!cards.length) { cards = Array.from(list.children).filter(function (c) { return c.tagName !== 'SCRIPT' && !c.classList.contains('u-display-none'); }); } if (!cards.length) return; /* Ensure cards start at position 0 */ resetCards(); if (document.readyState === 'complete') { setTimeout(recache, 300); } else { window.addEventListener('load', function () { setTimeout(recache, 300); }); } document.addEventListener('mousemove', function (e) { if (!ready || window.innerWidth <= 992) return; var rect = list.getBoundingClientRect(); var inside = e.clientX >= rect.left && e.clientX <= rect.right && e.clientY >= rect.top && e.clientY <= rect.bottom; if (!inside) { if (active) { /* Mouse just left — reset cards to flush left */ active = false; resetCards(); } return; } active = true; pendingX = e.clientX; if (!rafQueued) { rafQueued = true; requestAnimationFrame(applyMove); } }); } window.addEventListener('resize', function () { if (window.innerWidth > 992 && ready) { setTimeout(recache, 100); } }); setTimeout(function () { window.enableMouseFollow(); window.enableHeroSlider && window.enableHeroSlider(); }, 100); })(); /* BLOCK 3 — MOBILE DRAG SLIDER (<= 992px) */ (function () { if (window.__heroSliderInitialized_h7s9x) return; window.__heroSliderInitialized_h7s9x = true; var inst = null, ready = false; window.enableHeroSlider = function () { ready = true; if (window.innerWidth <= 992) initSlider(); }; function initSlider() { var list = document.querySelector('[data-hero-slider]'); if (!list || inst) return; var autoplay = list.dataset.autoplay !== 'false'; var infinite = list.dataset.infinite !== 'false'; var canDrag = list.dataset.heroDraggable !== 'false'; var orig = Array.from(list.querySelectorAll('[data-hero-card]')); if (!orig.length) { Array.from(list.children).forEach(function (c) { if (c.tagName !== 'SCRIPT' && !c.classList.contains('u-display-none')) c.setAttribute('data-hero-card', ''); }); orig = Array.from(list.querySelectorAll('[data-hero-card]')); } if (!orig.length) return; list.style.setProperty('gap', list.dataset.heroGap || '2rem'); if (infinite) { orig.map(function (c) { return c.cloneNode(true); }).forEach(function (c) { list.appendChild(c); }); orig.map(function (c) { return c.cloneNode(true); }).forEach(function (c) { list.appendChild(c); }); } var last = orig[orig.length - 1]; var lw = last.offsetLeft + last.offsetWidth - orig[0].offsetLeft; var spd = parseFloat(list.dataset.heroSpeed) || 80; var dirn = list.dataset.heroDirection || 'left'; var ppf = spd / 60; var slow = parseFloat(list.dataset.heroSlowSpeed) || 0.2; var hvr = list.dataset.heroHover || 'pause'; var DRAG_MULT = 1.4; var st = { pos:0, drag:false, started:false, anim:autoplay, raf:null, mult:1 }; var sx=0, sy=0, ds=0, vt=[], ct=0, cx=0, cy=0; function clamp(p) { if (!infinite) { var mx=-(lw-list.offsetWidth); return Math.max(mx,Math.min(0,p)); } while (p<-lw) p+=lw; while (p>0) p-=lw; return p; } function calcVel() { if (vt.length<2) return 0; var r=vt.slice(-5),tot=0; for(var i=1;i0)tot+=(r[i].x-r[i-1].x)/dt*16;} return tot/(r.length-1); } function tick() { if (!st.anim) return; if (autoplay) { st.pos=clamp(st.pos+(dirn==='left'?-ppf:ppf)*st.mult); if(!infinite){var mx=-(lw-list.offsetWidth);if((dirn==='left'&&st.pos<=mx)||(dirn==='right'&&st.pos>=0)){st.anim=false;return;}} } list.style.transform='translateX('+st.pos+'px)'; st.raf=requestAnimationFrame(tick); } function inertia(v) { var DECEL=0.96; st.anim=false; cancelAnimationFrame(st.raf); (function s(){ if(Math.abs(v)<0.3){st.anim=autoplay;st.mult=1;if(autoplay)tick();return;} st.pos=clamp(st.pos+v); list.style.transform='translateX('+st.pos+'px)'; v*=DECEL; st.raf=requestAnimationFrame(s); })(); } function noClick(e){e.preventDefault();e.stopPropagation();e.stopImmediatePropagation();} function down(e) { if(!canDrag)return; var px=e.type.includes('touch')?e.touches[0].clientX:e.clientX; var py=e.type.includes('touch')?e.touches[0].clientY:e.clientY; st.started=true;st.drag=false;st.anim=false; ct=Date.now();cx=px;cy=py; if(st.raf)cancelAnimationFrame(st.raf); sx=px;sy=py;vt=[{x:px,time:Date.now()}];ds=st.pos; list.classList.add('is-dragging'); } function move(e) { if(!st.started)return; var px=e.type.includes('touch')?e.touches[0].clientX:e.clientX; var py=e.type.includes('touch')?e.touches[0].clientY:e.clientY; var dx=px-sx,dy=py-sy; if(!st.drag&&(Math.abs(dx)>5||Math.abs(dy)>5)){ if(Math.abs(dx)>Math.abs(dy)){ st.drag=true;e.preventDefault(); list.querySelectorAll('[data-hero-card]').forEach(function(i){i.addEventListener('click',noClick,{capture:true});}); }else{st.started=false;st.anim=autoplay;if(autoplay)tick();return;} } if(!st.drag)return; e.preventDefault(); vt.push({x:px,time:Date.now()});if(vt.length>10)vt.shift(); st.pos=clamp(ds+(dx*DRAG_MULT));list.style.transform='translateX('+st.pos+'px)'; } function up(e) { if(!st.started)return; list.classList.remove('is-dragging'); var wd=st.drag; if(!st.drag){ var px=e.type.includes('touch')?e.changedTouches[0].clientX:e.clientX; var py=e.type.includes('touch')?e.changedTouches[0].clientY:e.clientY; if(Math.sqrt(Math.pow(px-cx,2)+Math.pow(py-cy,2))<=5&&Date.now()-ct<=300){ st.anim=autoplay;if(autoplay)tick();st.started=false;return; } } if(wd)setTimeout(function(){list.querySelectorAll('[data-hero-card]').forEach(function(i){i.removeEventListener('click',noClick,{capture:true});});},50); var v=calcVel(); if(Math.abs(v)>1){inertia(v);}else{st.anim=autoplay;if(autoplay)tick();} st.drag=false;st.started=false;vt=[]; } function onEnter(){if(st.drag||!st.anim)return;if(hvr==='pause'){st.anim=false;cancelAnimationFrame(st.raf);st.raf=null;}else if(hvr==='slow')st.mult=slow;} function onLeave(){if(st.drag)return;if(hvr==='pause'&&autoplay){st.anim=true;tick();}else if(hvr==='slow')st.mult=1;} if(canDrag){ list.addEventListener('mousedown',down); list.addEventListener('touchstart',down,{passive:true}); document.addEventListener('mousemove',move); document.addEventListener('touchmove',move,{passive:false}); document.addEventListener('mouseup',up); document.addEventListener('touchend',up); } if(hvr!=='none'){list.addEventListener('mouseenter',onEnter);list.addEventListener('mouseleave',onLeave);} list.addEventListener('contextmenu',function(e){e.preventDefault();}); list.addEventListener('dragstart',function(e){e.preventDefault();}); if(autoplay)tick(); inst={cleanup:function(){ if(st.raf)cancelAnimationFrame(st.raf); if(canDrag){list.removeEventListener('mousedown',down);list.removeEventListener('touchstart',down);document.removeEventListener('mousemove',move);document.removeEventListener('touchmove',move);document.removeEventListener('mouseup',up);document.removeEventListener('touchend',up);} list.removeEventListener('mouseenter',onEnter);list.removeEventListener('mouseleave',onLeave); if(infinite){var all=Array.from(list.querySelectorAll('[data-hero-card]'));all.slice(orig.length).forEach(function(c){c.remove();});} list.style.transform='';inst=null; }}; } window.addEventListener('resize',function(){ if(window.innerWidth<=992){if(!inst&&ready)initSlider();} else{if(inst)inst.cleanup();} }); })(); /* BLOCK 4 — CUSTOM CURSOR (document delegation — all cards) */ (function () { if (window.innerWidth <= 992) return; var cursor = document.createElement('div'); cursor.className = 'n4-cursor'; var txt = document.createElement('span'); txt.className = 'n4-cursor-text'; cursor.appendChild(txt); document.body.appendChild(cursor); var mx = -400, my = -400, cx2 = -400, cy2 = -400; function lag() { return Math.max(0.02, Math.min(0.5, parseFloat(cssVar('--cursor-lag', '0.10')))); } function off() { return parseFloat(cssVar('--cursor-offset', '0')) || 0; } document.addEventListener('mousemove', function (e) { mx = e.clientX + off(); my = e.clientY + off(); }); (function loop() { cx2 += (mx - cx2) * lag(); cy2 += (my - cy2) * lag(); cursor.style.left = cx2 + 'px'; cursor.style.top = cy2 + 'px'; requestAnimationFrame(loop); })(); document.addEventListener('mouseover', function (e) { var el = e.target.closest('[data-cursor-text]'); if (!el) return; txt.textContent = el.dataset.cursorText || ''; cursor.classList.add('visible'); }); document.addEventListener('mouseout', function (e) { var el = e.target.closest('[data-cursor-text]'); if (!el) return; if (!el.contains(e.relatedTarget)) { cursor.classList.remove('visible', 'dragging'); } }); document.addEventListener('mousedown', function (e) { if (e.target.closest('[data-cursor-text]')) cursor.classList.add('dragging'); }); document.addEventListener('mouseup', function () { cursor.classList.remove('dragging'); }); })(); /* BLOCK 5 — SWIPER */ (function () { function init() { var slow = window.matchMedia('(prefers-reduced-motion: reduce)').matches; document.querySelectorAll('[data-swiper]').forEach(function (el) { if (el.dataset.scriptInitialized) return; el.dataset.scriptInitialized = 'true'; new Swiper(el, { a11y:{slideRole:'listitem'}, slidesPerView:'auto', followFinger:true, freeMode:false, snapOnRelease:true, centeredSlides:false, preloadImages:false, initialSlide:0, autoHeight:false, speed:slow?0:300, slideActiveClass:'is-active', slideDuplicateActiveClass:'is-active', mousewheel:{forceToAxis:true}, keyboard:{enabled:true, onlyInViewport:true} }); }); } if (typeof Swiper !== 'undefined') { init(); } else { var c = setInterval(function () { if (typeof Swiper !== 'undefined') { clearInterval(c); init(); } }, 50); setTimeout(function () { clearInterval(c); }, 5000); } })(); });

what we do

Custom Development

Tailored digital solutions engineered from the ground up to match your business logic, performance needs, and long-term scalability goals.

Image gallery marquee
Image gallery marquee
Image gallery marquee
Image gallery marquee
Image gallery marquee
Image gallery marquee

Our Services

We develop fully custom web applications designed around your exact business requirements. From dashboards to internal tools and customer platforms, every system is built to solve real operational problems with clean architecture, fast performance, and scalable structure.

Frequently Asked Questions

Custom development is the process of building digital solutions from scratch based on specific business requirements. Unlike templates or pre-built systems, everything is designed and coded to match your exact workflow and functionality needs.
Custom development is ideal when your business requires unique features, complex workflows, integrations, or scalability that standard platforms cannot fully support.
Yes, for growing businesses. Templates are limited in flexibility, while custom development provides full control over design, performance, and functionality without unnecessary restrictions.
Absolutely. Clean, optimized code structures and tailored architecture significantly improve speed, responsiveness, and overall user experience compared to generic builds.
Yes. We can support maintenance, updates, feature expansion, and performance optimization to ensure your system continues to run smoothly as your business grows.
Yes. We integrate payment gateways, CRMs, analytics tools, marketing platforms, and any required third-party services into a unified system.
Yes. Every system is built with scalability in mind, allowing your platform to handle increased traffic, new features, and evolving business needs without major rebuilds.
Timelines depend on complexity and scope, but most custom projects range from a few weeks to several months, including planning, development, testing, and deployment.

Content Feed

Launch a business your audience will love — at speed.

Start a project
* DO NOT add defer / async / type attributes — paste the raw