diff --git a/components.d.ts b/components.d.ts
index 3e65c3cc..b87945f8 100644
--- a/components.d.ts
+++ b/components.d.ts
@@ -151,6 +151,7 @@ declare module '@vue/runtime-core' {
PercentageCalculator: typeof import('./src/tools/percentage-calculator/percentage-calculator.vue')['default']
PhoneParserAndFormatter: typeof import('./src/tools/phone-parser-and-formatter/phone-parser-and-formatter.vue')['default']
QrCodeGenerator: typeof import('./src/tools/qr-code-generator/qr-code-generator.vue')['default']
+ ContactQRCodeGenerator: typeof import('./src/tools/qr-contact-info-generator/qr-contact-info-generator.vue')['default']
RandomPortGenerator: typeof import('./src/tools/random-port-generator/random-port-generator.vue')['default']
RegexMemo: typeof import('./src/tools/regex-memo/regex-memo.vue')['default']
'RegexMemo.content': typeof import('./src/tools/regex-memo/regex-memo.content.md')['default']
diff --git a/src/tools/index.ts b/src/tools/index.ts
index 388cfaf4..c4be5a1e 100644
--- a/src/tools/index.ts
+++ b/src/tools/index.ts
@@ -1,6 +1,7 @@
import { tool as base64FileConverter } from './base64-file-converter';
import { tool as base64StringConverter } from './base64-string-converter';
import { tool as basicAuthGenerator } from './basic-auth-generator';
+import { tool as qrContactInfoGenerator } from './qr-contact-info-generator';
import { tool as emailNormalizer } from './email-normalizer';
import { tool as asciiTextDrawer } from './ascii-text-drawer';
diff --git a/src/tools/qr-contact-info-generator/contact-info-qr-code-generator.ts b/src/tools/qr-contact-info-generator/contact-info-qr-code-generator.ts
deleted file mode 100644
index 1b17d371..00000000
--- a/src/tools/qr-contact-info-generator/contact-info-qr-code-generator.ts
+++ /dev/null
@@ -1,49 +0,0 @@
-import QRCode from 'qrcode';
-
-interface ContactInfo {
- firstName: string;
- lastName: string;
- role: string;
- phoneNumber: string;
- email: string;
- companyName: string;
- companyWebsite: string;
- companyAddress: string;
-}
-
-const generateContactInfoQRCode = (contactInfo: ContactInfo): void => {
- const vCard = `
-BEGIN:VCARD
-VERSION:3.0
-N:${contactInfo.lastName};${contactInfo.firstName}
-FN:${contactInfo.firstName} ${contactInfo.lastName}
-ORG:${contactInfo.companyName}
-TITLE:${contactInfo.role}
-TEL;TYPE=WORK,VOICE:${contactInfo.phoneNumber}
-EMAIL;TYPE=PREF,INTERNET:${contactInfo.email}
-URL:${contactInfo.companyWebsite}
-ADR;TYPE=WORK,PREF:;;${contactInfo.companyAddress}
-END:VCARD
- `;
-
- QRCode.toDataURL(vCard, { errorCorrectionLevel: 'H' }, (err: Error | null, url: string) => {
- if (err) {
- console.error(err);
- return;
- }
- console.log(url);
- });
-};
-
-const contactInfo: ContactInfo = {
- firstName: 'John',
- lastName: 'Doe',
- role: 'Software Engineer',
- phoneNumber: '+1234567890',
- email: 'john.doe@example.com',
- companyName: 'Example Inc.',
- companyWebsite: 'https://www.example.com',
- companyAddress: '123 Example Street, City, Country'
-};
-
-generateContactInfoQRCode(contactInfo);
\ No newline at end of file
diff --git a/src/tools/qr-contact-info-generator/contact-info-qr-code-generator.vue b/src/tools/qr-contact-info-generator/contact-info-qr-code-generator.vue
deleted file mode 100644
index 46eb10d9..00000000
--- a/src/tools/qr-contact-info-generator/contact-info-qr-code-generator.vue
+++ /dev/null
@@ -1,160 +0,0 @@
-
-
-
Contact Info QR Code Generator
-
-
-
QR Code:
-
![Contact Info QR Code]()
-
-
-
-
-
-
-
\ No newline at end of file
diff --git a/src/tools/qr-contact-info-generator/index.ts b/src/tools/qr-contact-info-generator/index.ts
index fd467b19..ce087fad 100644
--- a/src/tools/qr-contact-info-generator/index.ts
+++ b/src/tools/qr-contact-info-generator/index.ts
@@ -1,5 +1,13 @@
-import ContactInfoQRCodeGenerator from './contact-info-qr-code-generator.vue';
+import { Qrcode } from '@vicons/tabler';
+import { defineTool } from '../tool';
+import { translate } from '@/plugins/i18n.plugin';
-export {
- ContactInfoQRCodeGenerator,
-};
\ No newline at end of file
+export const tool = defineTool({
+ name: translate('tools.qr-contact-info-generator.title'),
+ path: '/qr-contact-info-generator',
+ description: translate('tools.qr-contact-info-generator.description'),
+ keywords: ['qr', 'contact', 'info', 'generator'],
+ component: () => import('./qr-contact-info-generator.vue'),
+ icon: Qrcode,
+ createdAt: new Date('2025-02-17'),
+});
\ No newline at end of file
diff --git a/src/tools/qr-contact-info-generator/qr-contact-info-generator.ts b/src/tools/qr-contact-info-generator/qr-contact-info-generator.ts
new file mode 100644
index 00000000..9ce894e4
--- /dev/null
+++ b/src/tools/qr-contact-info-generator/qr-contact-info-generator.ts
@@ -0,0 +1,56 @@
+import { type MaybeRef, get } from '@vueuse/core';
+import QRCode, { type QRCodeErrorCorrectionLevel, type QRCodeToDataURLOptions } from 'qrcode';
+import { isRef, ref, watch } from 'vue';
+
+interface ContactInfo {
+ firstName: string;
+ lastName: string;
+ jobRole: string;
+ phoneNumber: string;
+ emailAddress: string;
+ companyName: string;
+ companyWebsite: string;
+ companyAddress: string;
+}
+
+interface QRCodeOptions {
+ foregroundColor?: string;
+ backgroundColor?: string;
+}
+
+export function generateContactQRCode(contact: MaybeRef, options: MaybeRef = {}): Promise {
+ const vCard = ref(`
+BEGIN:VCARD
+VERSION:3.0
+FN:${get(contact).firstName} ${get(contact).lastName}
+ORG:${get(contact).companyName}
+TITLE:${get(contact).jobRole}
+TEL:${get(contact).phoneNumber}
+EMAIL:${get(contact).emailAddress}
+URL:${get(contact).companyWebsite}
+ADR:${get(contact).companyAddress}
+END:VCARD
+ `);
+
+ const qrOptions: QRCodeToDataURLOptions = {
+ errorCorrectionLevel: 'H' as QRCodeErrorCorrectionLevel,
+ type: 'image/png',
+ margin: 1,
+ color: {
+ dark: get(options).foregroundColor || '#000000ff',
+ light: get(options).backgroundColor || '#ffffffff',
+ },
+ };
+
+ const qrCodeDataUrl = ref('');
+
+ watch(
+ [vCard, options].filter(isRef),
+ async () => {
+ qrCodeDataUrl.value = await QRCode.toDataURL(get(vCard), qrOptions);
+ },
+ { immediate: true },
+ );
+
+ return qrCodeDataUrl.value;
+}
\ No newline at end of file
diff --git a/src/tools/qr-contact-info-generator/qr-contact-info-generator.vue b/src/tools/qr-contact-info-generator/qr-contact-info-generator.vue
new file mode 100644
index 00000000..b61dfe61
--- /dev/null
+++ b/src/tools/qr-contact-info-generator/qr-contact-info-generator.vue
@@ -0,0 +1,77 @@
+
+
+
Contact QR Code Generator
+
+
+
![Contact QR Code]()
+
+
+
+
+
+
+
\ No newline at end of file