2012-04-06 31 views
9

Tôi có một QGraphicsScene với khoảng 1000 QGraphicsItems, đây là các mục vật lý thực sự. Mỗi khung hình họ tiến lên, kiểm tra va chạm, và giải quyết những va chạm đó, trong số những thứ khác. Tôi thực sự muốn có vật lý đa luồng.Ghép đa luồng cảnh vật lý Qt

Tôi hiểu rằng các lớp QGraphics không an toàn. Có nghĩa là, chúng chỉ có thể được gọi từ chủ đề chính. Điều này có buộc tôi gửi các thuộc tính mục cuối cùng (x, y, xoay) mỗi khung đến chuỗi chính bằng cách sử dụng cơ chế tín hiệu/khe, và sau đó sử dụng một phương thức chủ đề chính để thực sự cập nhật QGraphicsItems? Hay có cách nào dễ hơn để làm điều này?

Điều gì sau đây chỉ là giả thuyết: Tôi có thể sử dụng QtConcurrent để chạy một phương thức trong danh sách QGraphicsItems của mình không? Nếu tôi sử dụng QMutex trong phương pháp vẽ QGraphicsItem của tôi và QMutex trong phương pháp vật lý của tôi (điều này sẽ thay đổi các thuộc tính của QGraphicsItem), điều này có đảm bảo rằng chỉ có một luồng đang đọc/ghi mỗi QGraphicsItem tại bất kỳ thời điểm nào?

+0

Tôi đã đọc một số điều về cách sử dụng QueuedConnection khi kết nối tín hiệu/khe. Tôi đã không thử nó hoặc thậm chí nhìn vào các chi tiết, nhưng tôi nghĩ rằng nó có giá trị điều tra thêm. Có ai khác ngoài kia có kinh nghiệm với điều này không? – aldo

+0

Tôi đã sử dụng cổng Delphi của Box2D và tôi rất hài lòng với nó. Tại sao không thử? Đi đến [trang] này (http://labs.qt.nokia.com/2010/02/26/qt-box2d-is-easy/) nếu bạn quan tâm. – menjaraz

+0

Box2D trông thú vị, nhưng tôi không thấy bất cứ nơi nào mà nó đa luồng. – Joel

Trả lời

2
  1. Nếu tôi sử dụng một QMutex trong phương pháp sơn QGraphicsItem tôi và một QMutex trong phương pháp vật lý của tôi (mà sẽ thay đổi tính chất của QGraphicsItem của tôi), sẽ này đảm bảo rằng chỉ có một thread đang đọc/viết mỗi QGraphicsItem tại bất kỳ thời điểm nào trong thời gian?

    Không, không. QGraphicsItem được sử dụng nhiều trong khi vẽ, không chỉ có phương pháp paint được gọi. Hãy xem, ví dụ: here. Ngay cả khi nó có thể làm việc, nó sẽ là giải pháp xấu xí, bởi vì rõ ràng, QGraphicsItem có thể được sử dụng không chỉ để vẽ.

  2. Liệu lực lượng này tôi để gửi các tài sản chính thức mục (x, y, luân chuyển) mỗi khung để các chủ đề chính sử dụng một cơ chế tín hiệu/khe, và sau đó sử dụng một phương pháp chủ đề chính để thực sự cập nhật QGraphicsItems? Hoặc là có cách nào dễ hơn để thực hiện việc này không?

    Có, bạn phải di chuyển quá trình thay đổi mục sang chuỗi chính. Bạn thực sự có một số lựa chọn thay thế:

    • Sử dụng cơ chế tín hiệu/khe, như bạn đã đề cập.
    • Sử dụng meta-calls với QueuedConnection
    • Gửi sự kiện tùy chỉnh.

    Đừng quên, bạn có BlockingQueuedConnection, nếu bạn muốn đợi cho sơn xong.

    Ngoài ra, bạn có thể sử dụng tất cả công cụ này với QtConcurent.

Thực ra, việc quản lý không quá khó. Nó an toàn hơn và dễ dàng hơn, đảm bảo an toàn chủ đề theo cách thủ công.

Vấn đề lớn hơn là bạn có thể có thể thất bại ngay cả khi cố gắng để đọc mục (chỉ sử dụng const memebers, ví dụ) trong sợi nhân.

Cho đến nay, như QGraphicsItem không phải là chủ đề an toàn, thậm chí đọc là không phải. Và kinh nghiệm phát triển ứng dụng đa luồng của tôi trong Qt cho tôi biết rằng nếu có điều gì đó xấu có thể xảy ra, thì sẽ xảy ra.

+0

Cảm ơn câu trả lời. Một câu hỏi: Nếu tôi tạo một lớp kế thừa QGraphicsItem, và thêm một số thuộc tính tùy chỉnh (màu sắc, vận tốc, vv), tôi có thể sửa đổi các lớp đó từ một luồng khác không? Tôi có được miễn là tôi đảm bảo rằng chỉ có một chủ đề được đọc/ghi vào mỗi tài sản tại một thời điểm? – Joel

+0

@ Jelel, nếu họ không sử dụng các thành viên khác được thừa hưởng, bạn có thể. Nhưng tốt hơn tôi nên sử dụng tổng hợp thừa kế trong trường hợp này (_your_ bao gồm 'QGraphicsItem' làm một memeber), vì trong trường hợp này các thuộc tính này phục vụ một số mục tiêu riêng biệt, không thực sự là _extend_' QGraphicsItem'. Cá nhân tôi nghĩ, nó sẽ làm tăng sự rõ ràng. – Lol4t0

+0

Tôi không chắc làm thế nào một tập hợp sẽ làm việc trong trường hợp của tôi. Vì vậy, chúng tôi rõ ràng, tôi muốn lớp học của tôi để reimplement phương pháp sơn. Tôi không chắc làm thế nào tôi sẽ làm điều này mà không kế thừa QGraphicsItem. – Joel