CtrlK
BlogDocsLog inGet started
Tessl Logo

tessl/npm-tarojs--taro-h5

H5端API库,为Taro跨端开发框架提供Web/H5端的API实现

Pending
Overview
Eval results
Files

canvas.mddocs/

Canvas APIs

Canvas drawing and manipulation APIs providing basic HTML5 Canvas operations with Mini Program compatibility for 2D graphics and image processing.

Capabilities

Canvas Context Creation

Create and manage canvas contexts for drawing operations.

/**
 * Create canvas context for drawing operations
 * @param canvasId - Canvas element ID
 * @param componentInstance - Component instance (optional in H5)
 * @returns Canvas rendering context
 */
function createCanvasContext(canvasId: string, componentInstance?: any): CanvasContext;

interface CanvasContext {
  // Drawing operations
  fillRect(x: number, y: number, width: number, height: number): void;
  strokeRect(x: number, y: number, width: number, height: number): void;
  clearRect(x: number, y: number, width: number, height: number): void;
  
  // Path operations
  beginPath(): void;
  closePath(): void;
  moveTo(x: number, y: number): void;
  lineTo(x: number, y: number): void;
  arc(x: number, y: number, radius: number, startAngle: number, endAngle: number, counterclockwise?: boolean): void;
  
  // Styles
  setFillStyle(color: string): void;
  setStrokeStyle(color: string): void;
  setLineWidth(lineWidth: number): void;
  
  // Text
  fillText(text: string, x: number, y: number, maxWidth?: number): void;
  strokeText(text: string, x: number, y: number, maxWidth?: number): void;
  setFontSize(fontSize: number): void;
  
  // Images
  drawImage(imageResource: string, x: number, y: number): void;
  drawImage(imageResource: string, x: number, y: number, width: number, height: number): void;
  
  // Execute drawing
  draw(reserve?: boolean, callback?: () => void): void;
}

Canvas Image Operations

Extract and manipulate image data from canvas elements.

/**
 * Convert canvas content to temporary file path
 * @param options - Canvas export configuration
 * @returns Promise resolving to temporary file path
 */
function canvasToTempFilePath(options: CanvasToTempFilePathOption): Promise<CanvasToTempFilePathResult>;

/**
 * Get image data from canvas
 * @param options - Image data retrieval configuration
 * @returns Promise resolving to image data
 */
function canvasGetImageData(options: CanvasGetImageDataOption): Promise<CanvasGetImageDataResult>;

/**
 * Put image data to canvas
 * @param options - Image data insertion configuration
 * @returns Promise that resolves when data is inserted
 */
function canvasPutImageData(options: CanvasPutImageDataOption): Promise<void>;

interface CanvasToTempFilePathOption extends CallbackOptions {
  /** Canvas element ID */
  canvasId: string;
  /** Image file type (default: 'png') */
  fileType?: 'jpg' | 'png';
  /** Image quality (0-1, for jpg only) */
  quality?: number;
  /** Export width (default: canvas width) */
  destWidth?: number;
  /** Export height (default: canvas height) */
  destHeight?: number;
}

interface CanvasToTempFilePathResult {
  /** Temporary file path */
  tempFilePath: string;
}

interface CanvasGetImageDataOption extends CallbackOptions {
  /** Canvas element ID */
  canvasId: string;
  /** Start x coordinate */
  x: number;
  /** Start y coordinate */
  y: number;
  /** Width of image data area */
  width: number;
  /** Height of image data area */
  height: number;
}

interface CanvasGetImageDataResult {
  /** Image data array */
  data: Uint8ClampedArray;
  /** Image width */
  width: number;
  /** Image height */
  height: number;
}

interface CanvasPutImageDataOption extends CallbackOptions {
  /** Canvas element ID */
  canvasId: string;
  /** Image data array */
  data: Uint8ClampedArray;
  /** Start x coordinate */
  x: number;
  /** Start y coordinate */
  y: number;
  /** Image width */
  width: number;
  /** Image height */
  height: number;
}

Usage Examples:

import { 
  createCanvasContext, 
  canvasToTempFilePath, 
  canvasGetImageData, 
  canvasPutImageData 
} from "@tarojs/taro-h5";

// Basic canvas drawing
function drawOnCanvas() {
  const ctx = createCanvasContext('myCanvas');
  
  // Set styles
  ctx.setFillStyle('#ff0000');
  ctx.setStrokeStyle('#00ff00');
  ctx.setLineWidth(2);
  
  // Draw shapes
  ctx.fillRect(10, 10, 100, 100);
  ctx.strokeRect(120, 10, 100, 100);
  
  // Draw circle
  ctx.beginPath();
  ctx.arc(75, 200, 50, 0, 2 * Math.PI);
  ctx.setFillStyle('#0000ff');
  ctx.fill();
  
  // Draw text
  ctx.setFontSize(20);
  ctx.setFillStyle('#000000');
  ctx.fillText('Hello Canvas', 10, 300);
  
  // Execute drawing
  ctx.draw();
}

// Export canvas as image
async function exportCanvas() {
  try {
    const result = await canvasToTempFilePath({
      canvasId: 'myCanvas',
      fileType: 'png',
      quality: 1.0
    });
    
    console.log('Canvas exported to:', result.tempFilePath);
    return result.tempFilePath;
  } catch (error) {
    console.error('Canvas export failed:', error);
  }
}

// Image data manipulation
async function manipulateImageData() {
  try {
    // Get image data
    const imageData = await canvasGetImageData({
      canvasId: 'myCanvas',
      x: 0,
      y: 0,
      width: 300,
      height: 300
    });
    
    // Modify pixel data (invert colors)
    const data = new Uint8ClampedArray(imageData.data);
    for (let i = 0; i < data.length; i += 4) {
      data[i] = 255 - data[i];       // Red
      data[i + 1] = 255 - data[i + 1]; // Green
      data[i + 2] = 255 - data[i + 2]; // Blue
      // Alpha channel (i + 3) unchanged
    }
    
    // Put modified data back
    await canvasPutImageData({
      canvasId: 'myCanvas',
      data: data,
      x: 0,
      y: 0,
      width: imageData.width,
      height: imageData.height
    });
    
    console.log('Image data modified successfully');
  } catch (error) {
    console.error('Image data manipulation failed:', error);
  }
}

Not Implemented Canvas APIs

The following canvas APIs are not available in the H5 environment:

// ❌ Not implemented - Advanced canvas features
declare function createOffscreenCanvas(): never;

Note: createOffscreenCanvas is not supported in the H5 environment due to browser compatibility limitations. Use regular canvas elements with createCanvasContext instead.

Advanced Canvas Patterns

Complex canvas operations and optimization techniques.

// Canvas drawing manager
class CanvasManager {
  private context: CanvasContext;
  private canvasId: string;
  
  constructor(canvasId: string) {
    this.canvasId = canvasId;
    this.context = createCanvasContext(canvasId);
  }
  
  // Batch drawing operations
  batchDraw(operations: (() => void)[], reserve = false): Promise<void> {
    return new Promise((resolve) => {
      operations.forEach(op => op());
      this.context.draw(reserve, () => resolve());
    });
  }
  
  // Draw image with error handling
  async drawImageSafe(imageSrc: string, x: number, y: number, width?: number, height?: number): Promise<boolean> {
    return new Promise((resolve) => {
      try {
        if (width !== undefined && height !== undefined) {
          this.context.drawImage(imageSrc, x, y, width, height);
        } else {
          this.context.drawImage(imageSrc, x, y);
        }
        this.context.draw(false, () => resolve(true));
      } catch (error) {
        console.error('Failed to draw image:', error);
        resolve(false);
      }
    });
  }
  
  // Clear canvas
  clear(width: number, height: number): Promise<void> {
    return new Promise((resolve) => {
      this.context.clearRect(0, 0, width, height);
      this.context.draw(false, () => resolve());
    });
  }
  
  // Export canvas
  async exportAsImage(options: Partial<CanvasToTempFilePathOption> = {}): Promise<string | null> {
    try {
      const result = await canvasToTempFilePath({
        canvasId: this.canvasId,
        fileType: 'png',
        quality: 1.0,
        ...options
      });
      return result.tempFilePath;
    } catch (error) {
      console.error('Canvas export failed:', error);
      return null;
    }
  }
}

// Usage
const canvasManager = new CanvasManager('drawingCanvas');

// Batch drawing
await canvasManager.batchDraw([
  () => {
    canvasManager.context.setFillStyle('#ff0000');
    canvasManager.context.fillRect(0, 0, 100, 100);
  },
  () => {
    canvasManager.context.setFillStyle('#00ff00');
    canvasManager.context.fillRect(100, 0, 100, 100);
  }
]);

// Safe image drawing
const success = await canvasManager.drawImageSafe('/path/to/image.png', 50, 50, 200, 200);
if (success) {
  console.log('Image drawn successfully');
}

Performance Optimization

Best practices for canvas performance in web environments.

// Optimized canvas operations
class OptimizedCanvas {
  private context: CanvasContext;
  private operations: (() => void)[] = [];
  private drawPending = false;
  
  constructor(canvasId: string) {
    this.context = createCanvasContext(canvasId);
  }
  
  // Queue operations for batch execution
  queueOperation(operation: () => void): void {
    this.operations.push(operation);
    this.scheduleDraw();
  }
  
  private scheduleDraw(): void {
    if (this.drawPending) return;
    
    this.drawPending = true;
    requestAnimationFrame(() => {
      // Execute all queued operations
      this.operations.forEach(op => op());
      this.operations = [];
      
      // Single draw call
      this.context.draw();
      this.drawPending = false;
    });
  }
  
  // Immediate drawing (use sparingly)
  drawImmediate(operation: () => void): Promise<void> {
    return new Promise((resolve) => {
      operation();
      this.context.draw(false, () => resolve());
    });
  }
}

// Image caching for better performance
class ImageCache {
  private cache = new Map<string, boolean>();
  
  async preloadImage(src: string): Promise<boolean> {
    if (this.cache.has(src)) {
      return true;
    }
    
    return new Promise((resolve) => {
      const img = new Image();
      img.onload = () => {
        this.cache.set(src, true);
        resolve(true);
      };
      img.onerror = () => {
        resolve(false);
      };
      img.src = src;
    });
  }
  
  isImageLoaded(src: string): boolean {
    return this.cache.has(src);
  }
  
  async preloadImages(sources: string[]): Promise<boolean[]> {
    return Promise.all(sources.map(src => this.preloadImage(src)));
  }
}

Error Handling

Canvas operations can fail due to invalid parameters, missing resources, or browser limitations.

// Safe canvas operations
async function safeCanvasOperation<T>(
  operation: () => Promise<T>,
  fallback?: () => T,
  errorMessage = 'Canvas operation failed'
): Promise<T | null> {
  try {
    return await operation();
  } catch (error: any) {
    console.error(errorMessage, error);
    
    await showToast({
      title: errorMessage,
      icon: 'error'
    });
    
    return fallback ? fallback() : null;
  }
}

// Usage
const imagePath = await safeCanvasOperation(
  () => canvasToTempFilePath({
    canvasId: 'myCanvas',
    fileType: 'png'
  }).then(result => result.tempFilePath),
  () => '', // Fallback to empty string
  'Failed to export canvas'
);

Types

interface CallbackOptions {
  success?: (res: any) => void;
  fail?: (err: any) => void;
  complete?: (res: any) => void;
}

type ImageFileType = 'jpg' | 'png';
type FillStyle = string | CanvasGradient | CanvasPattern;
type StrokeStyle = string | CanvasGradient | CanvasPattern;

Install with Tessl CLI

npx tessl i tessl/npm-tarojs--taro-h5

docs

canvas.md

core-framework.md

device.md

dom-query.md

index.md

location.md

media.md

navigation.md

network.md

storage.md

system-info.md

ui-interactions.md

tile.json