2010-03-24 35 views
9

Trong ứng dụng của tôi, tôi cần một cái gì đó giống như một hệ thống hạt vì vậy tôi đã điều sau đây:Làm thế nào để hiển thị hiệu quả nhiều Hình ảnh? (IPhone lập trình)

Trong khi ứng dụng khởi Tôi tải một UIImage

laserImage = [UIImage imageNamed:@"laser.png"]; 

UIImage * laserImage được khai báo trong giao diện của Bộ điều khiển của tôi. Bây giờ mỗi khi tôi cần một hạt mới mã này làm cho con người:

// add new Laserimage 
UIImageView *newLaser = [[UIImageView alloc] initWithImage:laserImage]; 
[newLaser setTag:[model.lasers count]-9]; 
[newLaser setBounds:CGRectMake(0, 0, 17, 1)]; 
[newLaser setOpaque:YES]; 
[self.view addSubview:newLaser]; 
[newLaser release]; 

Xin lưu ý rằng những hình ảnh chỉ 17px * 1px nhỏ và model.lasers là một mảng nội bộ để làm tất cả những tính toán tách từ sản lượng đồ họa. Vì vậy, trong vòng lặp vẽ chính của tôi, tôi đặt tất cả các vị trí của UIImageView đến các vị trí tính theo model.lasers mảng của tôi:

for (int i = 0; i < [model.lasers count]; i++) { 
    [[self.view viewWithTag:i+10] setCenter:[[model.lasers objectAtIndex:i] pos]]; 
} 

tôi tăng lên các thẻ bằng cách 10 vì mặc định là 0 và tôi không muốn di chuyển tất cả các chế độ xem với thẻ mặc định.

Vì vậy, hoạt ảnh có vẻ đẹp với khoảng 10 - 20 hình ảnh nhưng thực sự chậm khi làm việc với khoảng 60 hình ảnh. Vì vậy, câu hỏi của tôi là: Có cách nào để tối ưu hóa điều này mà không cần bắt đầu lại trong OpenGl ES không?

Trả lời

8

Như jeff7 và FenderMostro đã nói, bạn đang sử dụng API cấp cao (UIKit) và bạn sẽ có hiệu suất tốt hơn bằng cách sử dụng API thấp hơn, CoreAnimation hoặc OpenGL. (Cocos2d được xây dựng trên đầu trang của OpenGL)

  • lựa chọn tốt nhất của bạn sẽ được sử dụng thay vì CALayers UIImageViews, có được một CGImageRef từ UIImage của bạn và thiết lập nó như là nội dung cho các lớp.

  • Ngoài ra, bạn có thể muốn giữ một nhóm CALayers và sử dụng lại chúng bằng cách ẩn/hiện khi cần thiết. 60 Calayers của 17 * 1 pixel không nhiều, tôi đã làm nó với hàng trăm người trong số họ mà không cần tối ưu hóa thêm.

Bằng cách này, hình ảnh sẽ được giải nén và có sẵn trong bộ nhớ video. Khi sử dụng UIKit, mọi thứ đều đi qua CPU, chưa kể đến việc tạo ra UIViews vốn là những đối tượng khá nặng.

+0

Đây là câu trả lời đúng. Mã của bạn sẽ hoạt động tốt miễn là CALayers sử dụng của bạn và có từng sử dụng cùng một layer.contents đặt cho cùng một hình ảnh CG. Việc thưởng cho toàn bộ trò chơi của bạn trong OpenGL sẽ là quá mức cần thiết, bạn chỉ cần không phân bổ tấn UIImageView, đó là gốc của vấn đề triển khai của bạn. Xem http://developer.apple.com/library/ios/#DOCUMENTATION/Cocoa/Conceptual/CoreAnimation_guide/SettingUpLayerObjects/SettingUpLayerObjects.html#//apple_ref/doc/uid/TP40004514-CH13-SW12 – MoDJ

0

Tôi muốn khuyên bạn nên bắt đầu sử dụng OpenGL ES, có một khung công tác tuyệt vời được gọi là cocos2d for iPhone có thể làm cho loại lập trình này rất dễ dàng và nhanh chóng. Từ xem nhanh mã của bạn, bạn có thể chỉnh sửa lại laser là CCSprite, đây là cách dễ dàng để di chuyển hình ảnh xung quanh một cảnh trong số nhiều thứ khác.

+0

Tôi chỉ xem nhanh cocos2d và có vẻ khá khả năng nhưng tôi gần hoàn thành ứng dụng và viết lại sẽ tốn quá nhiều thời gian. Bạn có ý tưởng nào khác không? – Thomas

1

UIImageView được tạo để hiển thị một hoặc nhiều hình ảnh. Vì vậy, thay vì tạo mỗi lần một UIImageView, bạn nên cân nhắc việc tạo một hình ảnh mới và thêm nó vào UIImageView để thay thế.

Xem here.

+0

Tài liệu của Apple cho biết UIImageView là để hiển thị một hình ảnh hoặc làm động một loạt hình ảnh. Vì tôi cần tất cả các hình ảnh được hiển thị cùng một lúc, tôi không thể sử dụng chức năng này ... Các ý tưởng khác? – Thomas

+0

ohh, xin lỗi Thomas, tôi không biết bắt đầu từ đâu. Chúng ta hãy chờ đợi nếu có một số câu trả lời khác từ cộng đồng. –

+0

Hi Thomas, vấn đề có thể là bạn đã không xóa bối cảnh vẽ. Bạn có thể kiểm tra lại điều đó không? –

3

Có vẻ như bạn đang cố gắng mã hóa trò chơi bằng cách sử dụng API UIKit, vốn không thực sự phù hợp với loại mục đích này. Bạn đang mở rộng tài nguyên của thiết bị bất cứ khi nào bạn phân bổ một UIView, điều này làm chậm quá trình tạo đối tượng là tốn kém. Bạn có thể có được hiệu suất bạn muốn bằng cách thả xuống CoreAnimation, điều này thực sự tốt khi vẽ hàng trăm hình ảnh trong một khung thời gian giới hạn, mặc dù nó vẫn tốt hơn nếu bạn sử dụng OpenGL hoặc một công cụ như Cocos2d.

Các vấn đề liên quan