Gerador de Voucher - AR7
by thvinic
HTML
<script src="https://cdnjs.cloudflare.com/ajax/libs/jspdf/2.5.1/jspdf.umd.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/html2canvas/1.4.1/html2canvas.min.js"></script>
<div class="container">
<!-- CABEÇALHO COM LOGO 312x218px -->
<div class="header">
<img alt="AR7-logo" class="" data-is360="0" src="https://i.ibb.co/tPQMxycG/instalador-de-ar-goiania-ar7-servicos.png" style="scale:0.6;float: inline-end;opacity: 50%;">
<h1>🧾 Gerador de Voucher</h1>
<div class="header-subtitle">JART77 - Ar Condicionado & Serviços</div>
</div>
<div class="form-section">
<div class="form-group">
<label for="clientName">Nome do Cliente *</label>
<input type="text" id="clientName" placeholder="Digite o nome completo do cliente" required>
</div>
<div class="form-group">
<label for="voucherValue">Valor do Voucher (1.230,00) *</label>
<input type="text" id="voucherValue" class="currency-input"
placeholder="1.230,00" maxlength="15" required>
</div>
<div class="form-group">
<label for="validityType">Validade do Voucher *</label>
<select id="validityType" onchange="toggleValidityField()">
<option value="date">Data específica</option>
<option value="indefinite">Indeterminado</option>
</select>
</div>
<div class="form-group" id="validityDateGroup">
<label for="validity">Data de Validade</label>
<input type="date" id="validity">
</div>
<div class="form-group">
<label for="reference">Referência do Voucher</label>
<input type="text" id="reference"...
CSS
* { margin: 0; padding: 0; box-sizing: border-box; }
body {
font-family: Arial, sans-serif;
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
min-height: 100vh; padding: 20px;
}
.container {
max-width: 850px; margin: 0 auto;
background: white; border-radius: 15px;
box-shadow: 0 20px 40px rgba(0,0,0,0.1); overflow: hidden;
}
.header {
background: linear-gradient(135deg, #2c3e50 0%, #3498db 50%, #2980b9 100%);
color: white; padding: 25px; text-align: center;
position: relative;
}
.header-logo {
width: 312px;
height: 218px;
object-fit: contain;
margin: 0 auto 15px;
display: block;
border-radius: 8px;
box-shadow: 0 8px 25px rgba(0,0,0,0.3);
border: 3px solid rgba(255,255,255,0.2);
}
.header h1 {
font-size: 2.2em;
margin-bottom: 5px;
text-shadow: 2px 2px 4px rgba(0,0,0,0.5);
}
.header-subtitle {
font-size: 1.2em;
opacity: 0.95;
font-weight: 500;
}
.form-section { padding: 40px; }
.form-group { margin-bottom: 25px; }
label {
display: block; font-weight: bold; color: #2c3e50;
margin-bottom: 8px; font-size: 1.1em;
}
input, select {
width: 100%; padding: 15px; border: 2px solid #ddd;
border-radius: 8px; font-size: 1.1em;
transition: border-color 0.3s;
}
input:focus, select:focus {
outline: none; border-color: #3498db;
box-shadow: 0 0 10px rgba(52,152,219,0.3);
}
.currency-input {
font-family: 'Courier New', monospace;
text-align: right;
...
JavaScript
document.addEventListener('DOMContentLoaded', function() {
const today = new Date();
today.setDate(today.getDate() + 30);
document.getElementById('validity').value = today.toISOString().split('T')[0];
const currencyInput = document.getElementById('voucherValue');
currencyInput.addEventListener('input', formatCurrencyInput);
});
// FUNÇÃO ATUALIZADA: Formata em tempo real enquanto digita
function formatCurrencyInput(e) {
let value = e.target.value.replace(/\D/g, ''); // Remove tudo que não é número
if (!value) {
e.target.value = '';
return;
}
// Transforma os números em decimais (ex: 1250 vira 12.50)
value = (parseFloat(value) / 100).toFixed(2);
// Formata para o padrão brasileiro (milhar com ponto, decimal com vírgula)
e.target.value = new Intl.NumberFormat('pt-BR', {
minimumFractionDigits: 2,
maximumFractionDigits: 2
}).format(value);
}
function parseCurrency(value) {
if (!value) return 0;
// Remove os pontos de milhar e substitui a vírgula por ponto para o JavaScript entender
return parseFloat(value.replace(/\./g, '').replace(',', '.')) || 0;
}
function formatCurrency(value) {
// Esta função é usada na exibição final do Voucher (com R$)
return new Intl.NumberFormat('pt-BR', {
style: 'currency',
currency: 'BRL'
}).format(value);
}
function toggleValidityField() {
const validityType = document.getElementById('validityType').value;
const validityDateGroup = document.getElementById('validityDateGroup');
validityDateGroup.style.display = (validityType === 'indefinite') ? 'none' : 'block';
}
function generateVoucher() {
const clientName = document.getElementById('clientName').value.trim();
const rawValue = document.getElementById('voucherValue').value.trim();
const validityType = document.getElementById('validityType').value;
const validityDate =...