Skip to content

Implement Web Beauty Effects

Integrate SDK

Install via npm:

bash
npm install facebetter

Using ES Module (Recommended):

javascript
import { 
  BeautyEffectEngine, 
  EngineConfig, 
  BeautyType, 
  BasicParam,
  ReshapeParam,
  MakeupParam,
  BackgroundMode,
  VirtualBackgroundOptions,
  ProcessMode 
} from 'facebetter';

Using CommonJS:

javascript
const { BeautyEffectEngine, EngineConfig } = require('facebetter');

Log Configuration

Logging is disabled by default, you can enable it as needed:

javascript
await engine.setLogConfig({
    consoleEnabled: true,  // Console logging
    fileEnabled: false,    // File logging (not supported in browser environment)
    level: 0,              // Log level: 0=DEBUG, 1=INFO, 2=WARN, 3=ERROR
    fileName: 'facebetter.log'  // Log file name (optional, only effective when fileEnabled is true)
});

Note: Log configuration must be called before engine initialization.

Create Engine Configuration

Follow the instructions on this page to get appId and appKey

javascript
import { BeautyEffectEngine, EngineConfig } from 'facebetter';

const config = new EngineConfig({
    appId: 'your appId',     // Configure your appid
    appKey: 'your appKey'    // Configure your appkey
});
const engine = new BeautyEffectEngine(config);

Error Handling

It's recommended to check if engine creation is successful:

javascript
try {
    await engine.init();
    console.log('Engine initialized successfully');
} catch (error) {
    console.error('Engine initialization failed:', error);
    // Handle error
}

Enable Effect Types

Beauty effects can be enabled/disabled by type. Enable corresponding beauty types based on subscription version, each type has corresponding parameters that can be adjusted.

javascript
import { BeautyType } from 'facebetter';

// Supported by all subscription versions
engine.setBeautyTypeEnabled(BeautyType.Basic, true);
// Supported by Pro, Pro+ versions
engine.setBeautyTypeEnabled(BeautyType.Reshape, true);
// Supported by Pro, Pro+ versions
engine.setBeautyTypeEnabled(BeautyType.Makeup, true);
// Only supported by Pro+ version
engine.setBeautyTypeEnabled(BeautyType.VirtualBackground, true);

Check Operation Results

All API calls should check return values or use try-catch:

javascript
import { BeautyType } from 'facebetter';

try {
    engine.setBeautyTypeEnabled(BeautyType.Basic, true);
    console.log('Successfully enabled basic beauty');
} catch (error) {
    console.error('Failed to enable basic beauty:', error);
}

Adjust Beauty Parameters

Set Skin Beauty Parameters

Use setBasicParam interface to set skin beauty parameters, parameter range [0.0, 1.0] (float);

javascript
import { BasicParam } from 'facebetter';

engine.setBasicParam(
    BasicParam.Smoothing, 
    0.5  // 0.0-1.0
);

Supported skin beauty parameters:

javascript
BasicParam = {
    Smoothing: 0,   // Skin smoothing
    Sharpening: 1,  // Sharpening
    Whitening: 2,   // Whitening
    Rosiness: 3     // Rosiness
};

Set Face Reshape Parameters

Use setReshapeParam interface to set face reshape parameters, parameter range [0.0, 1.0] (float);

javascript
import { ReshapeParam } from 'facebetter';

engine.setReshapeParam(
    ReshapeParam.FaceThin, 
    0.5  // 0.0-1.0
);

Supported face reshape parameters:

javascript
ReshapeParam = {
    FaceThin: 0,      // Face thinning
    FaceVShape: 1,    // V-face
    FaceNarrow: 2,    // Narrow face
    FaceShort: 3,     // Short face
    Cheekbone: 4,     // Cheekbone
    Jawbone: 5,       // Jawbone
    Chin: 6,          // Chin
    NoseSlim: 7,      // Nose slimming
    EyeSize: 8,       // Eye enlargement
    EyeDistance: 9    // Eye distance
};

Set Makeup Parameters

Use setMakeupParam interface to set makeup parameters, parameter range [0.0, 1.0] (float);

javascript
import { MakeupParam } from 'facebetter';

engine.setMakeupParam(
    MakeupParam.Lipstick, 
    0.5  // 0.0-1.0
);

Supported makeup parameters:

javascript
MakeupParam = {
    Lipstick: 0,  // Lipstick
    Blush: 1      // Blush
};

Set Virtual Background

Enable virtual background via setBeautyTypeEnabled interface:

javascript
engine.setBeautyTypeEnabled(BeautyType.VirtualBackground, true);

Set virtual background via setVirtualBackground interface (unified API, consistent with other platforms):

javascript
import { VirtualBackgroundOptions, BackgroundMode } from 'facebetter';

// Set blur background
const blurOptions = new VirtualBackgroundOptions({
  mode: BackgroundMode.Blur
});
engine.setVirtualBackground(blurOptions);

// Set image background
const bgImage = new Image();
bgImage.onload = () => {
  const imageOptions = new VirtualBackgroundOptions({
    mode: BackgroundMode.Image,
    backgroundImage: bgImage
  });
  engine.setVirtualBackground(imageOptions);
};
bgImage.src = 'background.jpg';

// Disable virtual background
const noneOptions = new VirtualBackgroundOptions({
  mode: BackgroundMode.None
});
engine.setVirtualBackground(noneOptions);

Simplified syntax (also supported):

javascript
// Pass object directly, no need to use new VirtualBackgroundOptions
engine.setVirtualBackground({
  mode: BackgroundMode.Blur
});

// Set image background
bgImage.onload = () => {
  engine.setVirtualBackground({
    mode: BackgroundMode.Image,
    backgroundImage: bgImage
  });
};

Process Images

Get Image Data from Canvas

javascript
const canvas = document.getElementById('canvas');
const ctx = canvas.getContext('2d');
const imageData = ctx.getImageData(0, 0, canvas.width, canvas.height);

Get Image Data from Image Element

javascript
const img = new Image();
img.onload = function() {
    const canvas = document.createElement('canvas');
    canvas.width = img.width;
    canvas.height = img.height;
    const ctx = canvas.getContext('2d');
    ctx.drawImage(img, 0, 0);
    const imageData = ctx.getImageData(0, 0, canvas.width, canvas.height);
    // Process image...
};
img.src = 'image.jpg';

Process Image

processMode includes Video and Image modes. Video is suitable for live streaming and video scenarios with higher efficiency, Image mode is suitable for image processing scenarios.

javascript
import { ProcessMode } from 'facebetter';

// processImage is a synchronous method (no await needed)
// Method 1: Pass ImageData with dimensions
const result = engine.processImage(
    imageData, 
    canvas.width, 
    canvas.height, 
    ProcessMode.Video  // or ProcessMode.Image
);

// Method 2: Pass HTMLImageElement (width/height can be omitted)
const result = engine.processImage(
    imageElement, 
    undefined, 
    undefined, 
    ProcessMode.Image
);

// Method 3: Pass HTMLVideoElement (width/height can be omitted)
const result = engine.processImage(
    videoElement, 
    undefined, 
    undefined, 
    ProcessMode.Video
);

// Method 4: Pass Uint8ClampedArray (width/height are required)
const result = engine.processImage(
    uint8Array, 
    640,  // required
    480,  // required
    ProcessMode.Video
);

Draw Processed Image

javascript
// Draw processed image data to Canvas
ctx.putImageData(result, 0, 0);

Save Processed Image

Processed image data can be saved as image files:

Method 1: Using Canvas.toDataURL()

javascript
// Draw processed image data to Canvas
ctx.putImageData(result, 0, 0);

// Convert to Data URL
const dataURL = canvas.toDataURL('image/png');

// Create download link
const link = document.createElement('a');
link.download = 'beauty-result.png';
link.href = dataURL;
link.click();

Method 2: Using Canvas.toBlob()

javascript
// Draw processed image data to Canvas
ctx.putImageData(result, 0, 0);

// Convert to Blob
canvas.toBlob(function(blob) {
    // Create download link
    const url = URL.createObjectURL(blob);
    const link = document.createElement('a');
    link.download = 'beauty-result.png';
    link.href = url;
    link.click();
    
    // Release URL object
    URL.revokeObjectURL(url);
}, 'image/png');

Method 3: Save as Different Formats

javascript
// Save as PNG (lossless, larger file size)
const pngDataURL = canvas.toDataURL('image/png');

// Save as JPEG (lossy, smaller file size, quality can be set)
const jpegDataURL = canvas.toDataURL('image/jpeg', 0.9); // Quality 0-1

// Create download
function downloadImage(dataURL, filename, mimeType) {
    const link = document.createElement('a');
    link.download = filename;
    link.href = dataURL;
    link.click();
}

// Usage
downloadImage(pngDataURL, 'beauty-result.png', 'image/png');
downloadImage(jpegDataURL, 'beauty-result.jpg', 'image/jpeg');

Complete Example: Save Processed Image

javascript
function processAndSaveImage(imageData, engine) {
    try {
        // Process image (synchronous method)
        const result = engine.processImage(
            imageData, 
            imageData.width, 
            imageData.height, 
            ProcessMode.Image
        );
        
        // Create temporary Canvas
        const canvas = document.createElement('canvas');
        canvas.width = imageData.width;
        canvas.height = imageData.height;
        const ctx = canvas.getContext('2d');
        
        // Draw processed image
        ctx.putImageData(result, 0, 0);
        
        // Save as image
        canvas.toBlob(function(blob) {
            const url = URL.createObjectURL(blob);
            const link = document.createElement('a');
            link.download = `beauty-${Date.now()}.png`;
            link.href = url;
            link.click();
            URL.revokeObjectURL(url);
        }, 'image/png');
        
        console.log('Image saved successfully');
    } catch (error) {
        console.error('Failed to process or save image:', error);
    }
}

Lifecycle Management

Release Resources

When page unloads or no longer in use, be sure to release engine resources:

javascript
// On page unload
window.addEventListener('beforeunload', () => {
    if (engine) {
        engine.destroy();
        engine = null;
    }
});

// Or in component destruction (Vue/React)
onUnmounted(() => {  // Vue
    if (engine) {
        engine.destroy();
        engine = null;
    }
});

useEffect(() => {  // React
    return () => {
        if (engine) {
            engine.destroy();
            engine = null;
        }
    };
}, []);

Memory Management

  • Release unused ImageData objects promptly
  • Avoid repeatedly creating large numbers of image objects in loops
  • Recommend reusing Canvas and ImageData objects
javascript
// Reuse Canvas and ImageData
let canvas = null;
let imageData = null;

function processFrame() {
    if (!canvas) {
        canvas = document.createElement('canvas');
        canvas.width = 640;
        canvas.height = 480;
    }
    
    const ctx = canvas.getContext('2d');
    // Draw image to canvas
    ctx.drawImage(video, 0, 0);
    
    // Get image data
    imageData = ctx.getImageData(0, 0, canvas.width, canvas.height);
    
    // Process image (synchronous method)
    const result = engine.processImage(
        imageData, 
        canvas.width, 
        canvas.height, 
        ProcessMode.Video
    );
    
    // Draw result
    ctx.putImageData(result, 0, 0);
}
  • Best Practices - Performance optimization and architecture design recommendations
  • FAQ - Common questions and troubleshooting
  • API Reference - Complete API documentation