The Couple Name Combiner is a fun and creative tool that blends two names into unique couple names, nicknames, or initials. Whether you’re celebrating a relationship, creating wedding décor, personalizing gifts, or just having fun with friends, this tool generates stylish combinations in seconds. Simple, quick, and designed to spark connection, perfect for couples, besties, and even brands looking for memorable mashups.
<!doctype html>
<html lang="en">
<head>
<meta charset="utf-8" />
<meta name="viewport" content="width=device-width,initial-scale=1" />
<title>Couple Name Combiner</title>
<style>
:root{--bg:#f9fafb;--card:#ffffff;--muted:#6b7280;--accent1:#ff6b9a;--accent2:#ff9a6b;--text:#1f2937}
*{box-sizing:border-box}
body{font-family:Inter,system-ui,Segoe UI,Roboto,Arial;min-height:100vh;margin:0;display:flex;align-items:center;justify-content:center;background:var(--bg);color:var(--text);padding:24px}
.widget{width:100%;max-width:760px;background:var(--card);border-radius:12px;padding:18px;border:1px solid #e5e7eb;box-shadow:0 6px 20px rgba(0,0,0,0.05)}
.head{display:flex;gap:12px;align-items:center;margin-bottom:12px}
.logo{width:56px;height:56px;border-radius:10px;display:flex;align-items:center;justify-content:center;background:linear-gradient(135deg,var(--accent1),var(--accent2));font-weight:700;color:white}
h1{font-size:18px;margin:0}
p.lead{margin:0;color:var(--muted);font-size:13px}
.form{display:grid;grid-template-columns:1fr 1fr auto;gap:10px;margin-top:14px}
input[type=text]{width:100%;padding:10px 12px;border-radius:8px;border:1px solid #d1d5db;background:#f9fafb;color:var(--text)}
.controls{display:flex;flex-direction:column;gap:8px}
.btn{display:inline-block;padding:10px 14px;border-radius:8px;background:linear-gradient(90deg,var(--accent1),var(--accent2));color:white;text-decoration:none;border:none;cursor:pointer;font-weight:600}
.btn.ghost{background:#f3f4f6;border:1px solid #d1d5db;color:var(--muted)}
.options{display:flex;gap:8px;align-items:center;margin-top:12px}
.chips{display:flex;gap:8px;flex-wrap:wrap}
.chip{padding:8px 10px;border-radius:999px;background:#f3f4f6;border:1px solid #e5e7eb;cursor:pointer;font-size:13px;color:var(--text)}
.chip.active{background:linear-gradient(90deg,var(--accent1),var(--accent2));color:white;border:none}
.results{margin-top:16px;display:grid;grid-template-columns:1fr 260px;gap:12px}
.list{background:#f9fafb;padding:12px;border-radius:10px;border:1px solid #e5e7eb;min-height:160px}
ul{list-style:none;padding:0;margin:0}
li{padding:8px;border-radius:8px;margin-bottom:8px;background:#ffffff;border:1px solid #e5e7eb;display:flex;justify-content:space-between;align-items:center}
.small{font-size:13px;color:var(--muted)}
.actions{display:flex;gap:8px}
.aside{background:#f9fafb;padding:12px;border-radius:10px;border:1px solid #e5e7eb;height:100%}
.aside h3{margin:0 0 8px 0}
@media (max-width:760px){.form{grid-template-columns:1fr 1fr;}.results{grid-template-columns:1fr}}
</style>
</head>
<body>
<div class="widget" role="application" aria-label="Couple Name Combiner">
<div class="head">
<div class="logo">CN</div>
<div>
<h1>Couple Name Combiner</h1>
<p class="lead">Blend two names into cute couple names, nicknames, initials and keepsake text.</p>
</div>
</div>
<div class="form">
<input id="nameA" type="text" placeholder="Enter name 1 (e.g., Alex)" />
<input id="nameB" type="text" placeholder="Enter name 2 (e.g., Jamie)" />
<div class="controls">
<button id="gen" class="btn">Generate</button>
<button id="clear" class="btn ghost">Clear</button>
</div>
</div>
<div class="options">
<div class="chips" role="tablist">
<button class="chip active" data-mode="blend">Blend (half/half)</button>
<button class="chip" data-mode="prefix">Prefix + Suffix</button>
<button class="chip" data-mode="interleave">Interleave</button>
<button class="chip" data-mode="concat">Concatenate</button>
</div>
<div style="margin-left:auto" class="small">Tip: try different modes for varied results</div>
</div>
<div class="results">
<div class="list" id="out">
<ul id="resultsList"><li class="small">No results yet — enter names and hit Generate.</li></ul>
</div>
<aside class="aside">
<h3>Your Picks</h3>
<div id="picked" class="small">No picks yet.</div>
<div class="actions" style="margin-top:10px">
<button id="copyPicked" class="btn ghost">Copy picked</button>
<button id="openSite" class="btn">Visit site</button>
</div>
</aside>
</div>
</div>
<script>
// Simple generator functions
const el = id => document.getElementById(id);
const chips = Array.from(document.querySelectorAll('.chip'));
let mode = 'blend';
chips.forEach(c=>c.addEventListener('click', ()=>{chips.forEach(x=>x.classList.remove('active'));c.classList.add('active');mode=c.dataset.mode;}));
function splitHalf(s){ const m=Math.ceil(s.length/2); return [s.slice(0,m), s.slice(m)]; }
function blend(a,b){ if(!a||!b) return []; const [a1,a2]=splitHalf(a); const [b1,b2]=splitHalf(b); return [a1+b2, b1+a2, a1+b1, a2+b2]; }
function prefixSuffix(a,b){ if(!a||!b) return []; return [a.slice(0,3)+b.slice(-3), a.slice(0,2)+b.slice(-4), b.slice(0,3)+a.slice(-3)]; }
function interleave(a,b){ if(!a||!b) return []; let out=''; for(let i=0;i<Math.max(a.length,b.length);i++){ if(a[i]) out+=a[i]; if(b[i]) out+=b[i]; } return [out]; }
function concatVariants(a,b){ if(!a||!b) return []; return [a+b, b+a, a+' & '+b, a+'-'+b]; }
function sanitize(s){ return s.trim().replace(/[^\p{L}\p{N} ]/gu,''); }
function generate(){ const a=sanitize(el('nameA').value); const b=sanitize(el('nameB').value); if(!a||!b){ alert('Please enter both names'); return; }
let arr=[];
if(mode==='blend') arr=blend(a,b);
else if(mode==='prefix') arr=prefixSuffix(a,b);
else if(mode==='interleave') arr=interleave(a,b);
else arr=concatVariants(a,b);
// add some variations
arr = Array.from(new Set(arr.concat(arr.map(x=>capitalize(x)), arr.map(x=>x.toLowerCase()))));
renderResults(arr);
}
function capitalize(s){ return s.split(' ').map(p=>p.charAt(0).toUpperCase()+p.slice(1)).join(''); }
function renderResults(list){ const ul=el('resultsList'); ul.innerHTML=''; list.forEach(item=>{ const li=document.createElement('li'); const span=document.createElement('span'); span.textContent=item; const btn=document.createElement('button'); btn.className='btn ghost'; btn.textContent='Pick'; btn.addEventListener('click', ()=>pick(item)); li.appendChild(span); li.appendChild(btn); ul.appendChild(li); }); if(list.length===0) ul.innerHTML='<li class="small">No results.</li>'; }
function pick(item){ el('picked').textContent = item; }
el('gen').addEventListener('click', generate);
el('clear').addEventListener('click', ()=>{ el('nameA').value=''; el('nameB').value=''; el('resultsList').innerHTML='<li class="small">No results yet — enter names and hit Generate.</li>'; el('picked').textContent='No picks yet.'; });
el('copyPicked').addEventListener('click', ()=>{ const txt = el('picked').textContent; if(!txt||txt==='No picks yet.') return alert('No pick to copy'); navigator.clipboard.writeText(txt).then(()=>alert('Copied!')) });
el('openSite').addEventListener('click', ()=> window.open('https://couplenamecombination.net/','_blank'));
// quick demo defaults
el('nameA').value='Jasmine'; el('nameB').value='James';
</script>
</body>
</html>
Top comments (0)