Skip to main content

用相机拍照

现在是有趣的部分 - 添加使用 Capacitor 相机接口 使用设备相机拍照的功能。我们将从为网络构建它开始,然后进行一些小调整以使其在移动设备(iOS 和 Android)上运行。

¥Now for the fun part - adding the ability to take photos with the device’s camera using the Capacitor Camera API. We’ll begin with building it for the web, then make some small tweaks to make it work on mobile (iOS and Android).

照片服务

¥Photo Service

所有 Capacitor 逻辑(相机使用和其他原生功能)都将封装在服务类中。使用 ionic generate 命令创建 PhotoService

¥All Capacitor logic (Camera usage and other native features) will be encapsulated in a service class. Create PhotoService using the ionic generate command:

ionic g service services/photo

打开新的 services/photo.service.ts 文件,让我们添加为相机功能提供支持的逻辑。首先,导入 Capacitor 依赖并获取对相机、文件系统和存储插件的引用:

¥Open the new services/photo.service.ts file, and let’s add the logic that will power the camera functionality. First, import Capacitor dependencies and get references to the Camera, Filesystem, and Storage plugins:



import { Camera, CameraResultType, CameraSource, Photo } from '@capacitor/camera';




import { Filesystem, Directory } from '@capacitor/filesystem';




import { Preferences } from '@capacitor/preferences';


接下来,定义一个新的类方法 addNewToGallery,它将包含拍摄设备照片并将其保存到文件系统的核心逻辑。让我们首先打开设备摄像头:

¥Next, define a new class method, addNewToGallery, that will contain the core logic to take a device photo and save it to the filesystem. Let’s start by opening the device camera:

public async addNewToGallery() {
// Take a photo
const capturedPhoto = await Camera.getPhoto({
resultType: CameraResultType.Uri,
source: CameraSource.Camera,
quality: 100
});
}

注意这里的魔力:没有特定于平台的代码(Web、iOS 或 Android)!Capacitor Camera 插件为我们抽象了这一点,只留下一个方法调用 - Camera.getPhoto() - 这将打开设备的相机并允许我们拍照。

¥Notice the magic here: there's no platform-specific code (web, iOS, or Android)! The Capacitor Camera plugin abstracts that away for us, leaving just one method call - Camera.getPhoto() - that will open up the device's camera and allow us to take photos.

接下来,打开 tab2.page.ts 并导入 PhotoService 类,并添加一个在导入的服务上调用 addNewToGallery 方法的方法:

¥Next, open up tab2.page.ts and import the PhotoService class and add a method that calls the addNewToGallery method on the imported service:

import { PhotoService } from '../services/photo.service';

constructor(public photoService: PhotoService) { }

addPhotoToGallery() {
this.photoService.addNewToGallery();
}

然后,打开 tab2.page.html 并在点击/单击 FAB 时调用 addPhotoToGallery() 函数:

¥Then, open tab2.page.html and call the addPhotoToGallery() function when the FAB is tapped/clicked:

<ion-content>
<ion-fab vertical="bottom" horizontal="center" slot="fixed">
<ion-fab-button (click)="addPhotoToGallery()">
<ion-icon name="camera"></ion-icon>
</ion-fab-button>
</ion-fab>
</ion-content>

保存文件,如果它尚未运行,请通过运行 ionic serve 在浏览器中重新启动开发服务器。在照片库选项卡上,单击相机按钮。如果你的计算机有任何类型的网络摄像头,则会出现一个模式窗口。来张自拍照吧!

¥Save the file, and if it's not running already, restart the development server in your browser by running ionic serve. On the Photo Gallery tab, click the Camera button. If your computer has a webcam of any sort, a modal window appears. Take a selfie!

A photo gallery app displaying a webcam selfie.

(你的自拍可能比我的好得多)

¥*(Your selfie is probably much better than mine)*

拍完照片后,它立即消失。我们需要在我们的应用中显示它并保存它以供将来访问。

¥After taking a photo, it disappears right away. We need to display it within our app and save it for future access.

显示照片

¥Displaying Photos

PhotoService 类定义之外(文件的最底部),创建一个新接口 UserPhoto 来保存我们的照片元数据:

¥Outside of the PhotoService class definition (the very bottom of the file), create a new interface, UserPhoto, to hold our photo metadata:

export interface UserPhoto {
filepath: string;
webviewPath?: string;
}

回到文件顶部,定义一个照片数组,其中包含对相机拍摄的每张照片的引用。

¥Back at the top of the file, define an array of Photos, which will contain a reference to each photo captured with the Camera.

export class PhotoService {
public photos: UserPhoto[] = [];

// other code
}

addNewToGallery 函数中,将新拍摄的照片添加到 Photos 数组的开头。

¥Over in the addNewToGallery function, add the newly captured photo to the beginning of the Photos array.

  const capturedPhoto = await Camera.getPhoto({
resultType: CameraResultType.Uri,
source: CameraSource.Camera,
quality: 100
});

this.photos.unshift({
filepath: "soon...",
webviewPath: capturedPhoto.webPath!
});
}

接下来,移至 tab2.page.html,以便我们可以在屏幕上显示图片。添加 网格组件,以便在将照片添加到图库时每张照片都能很好地显示,并循环遍历 PhotoServices 的照片数组中的每张照片,为每张照片添加一个图片组件 (<ion-img>)。将 src(源)指向照片的路径:

¥Next, move over to tab2.page.html so we can display the image on the screen. Add a Grid component so that each photo will display nicely as photos are added to the gallery, and loop through each photo in the PhotoServices's Photos array, adding an Image component (<ion-img>) for each. Point the src (source) at the photo’s path:

<ion-content>
<ion-grid>
<ion-row>
<ion-col size="6" *ngFor="let photo of photoService.photos; index as position">
<ion-img [src]="photo.webviewPath"></ion-img>
</ion-col>
</ion-row>
</ion-grid>

<!-- ion-fab markup -->
</ion-content>

保存所有文件。在网络浏览器中,单击相机按钮并拍摄另一张照片。这次,照片显示在照片库中!

¥Save all files. Within the web browser, click the Camera button and take another photo. This time, the photo is displayed in the Photo Gallery!

接下来,我们将添加对将照片保存到文件系统的支持,以便稍后可以在我们的应用中检索和显示它们。

¥Up next, we’ll add support for saving the photos to the filesystem, so they can be retrieved and displayed in our app at a later time.