Câu trả lời ngắn
MVC của Qt chỉ áp dụng cho một cấu trúc dữ liệu . Khi nói về một ứng dụng MVC, bạn không nên nghĩ đến QAbstractItemModel
hoặc QListView
.
Nếu bạn muốn có một kiến trúc MVC cho toàn bộ chương trình của mình, Qt không có một khung mô hình / khung nhìn "khổng lồ" như vậy. Nhưng đối với mỗi danh sách / cây dữ liệu trong chương trình của bạn, bạn có thể sử dụng phương pháp Qt MVC thực sự có một bộ điều khiển trong chế độ xem của nó. Các dữ liệu nằm trong hoặc bên ngoài của mô hình; điều này phụ thuộc vào loại mô hình bạn đang sử dụng (lớp con của mô hình riêng: có thể nằm trong mô hình; ví dụ: QSqlTableModel: bên ngoài (nhưng có thể được lưu trong bộ nhớ cache bên trong) mô hình). Để kết hợp các mô hình và khung nhìn của bạn với nhau, hãy sử dụng các lớp riêng sau đó triển khai logic nghiệp vụ .
Câu trả lời dài
Phương pháp tiếp cận mô hình / chế độ xem và thuật ngữ của Qt:
Qt cung cấp các khung nhìn đơn giản cho các mô hình của họ. Chúng có một bộ điều khiển được tích hợp sẵn: chọn, chỉnh sửa và di chuyển các mục là thứ mà trong hầu hết các trường hợp, bộ điều khiển "điều khiển". Đó là, diễn giải đầu vào của người dùng (nhấp chuột và di chuyển) và đưa ra các lệnh thích hợp cho mô hình.
Các mô hình của Qt thực sự là các mô hình có dữ liệu cơ bản. Tất nhiên, các mô hình trừu tượng không chứa dữ liệu, vì Qt không biết bạn muốn lưu trữ chúng như thế nào. Nhưng bạn mở rộng QAbstractItemModel theo nhu cầu của mình bằng cách thêm vùng chứa dữ liệu của bạn vào lớp con và làm cho giao diện mô hình truy cập dữ liệu của bạn. Vì vậy, trên thực tế, và tôi cho rằng bạn không thích điều này, vấn đề là bạn cần lập trình mô hình, vì vậy dữ liệu được truy cập và sửa đổi như thế nào trong cấu trúc dữ liệu của bạn.
Trong thuật ngữ MVC, mô hình chứa cả dữ liệu và logic . Trong Qt, việc bạn đưa một số logic kinh doanh vào trong mô hình của mình hay đưa nó ra bên ngoài, tùy thuộc vào bạn. Thậm chí không rõ ràng logic nghĩa là gì: Chọn, đổi tên và di chuyển các mục? => đã được thực hiện. Làm phép tính với chúng? => Đặt nó bên ngoài hoặc bên trong lớp con của mô hình. Lưu trữ hoặc tải dữ liệu từ / vào một tệp? => Đặt nó bên trong lớp con của mô hình.
Quan điểm cá nhân của tôi:
Rất khó để cung cấp một hệ thống MV (C) tốt và chung chung cho một lập trình viên. Bởi vì trong hầu hết các trường hợp, các mô hình là đơn giản (ví dụ: chỉ có danh sách chuỗi) Qt cũng cung cấp một QStringListModel sẵn sàng sử dụng. Nhưng nếu dữ liệu của bạn phức tạp hơn chuỗi, bạn muốn thể hiện dữ liệu như thế nào qua giao diện xem / mô hình Qt. Ví dụ: nếu bạn có một cấu trúc có 3 trường (giả sử những người có tên, tuổi và giới tính), bạn có thể gán 3 trường cho 3 cột khác nhau hoặc cho 3 vai trò khác nhau. Tôi không thích cả hai cách tiếp cận.
Tôi nghĩ rằng khung mô hình / khung nhìn của Qt chỉ hữu ích khi bạn muốn hiển thị các cấu trúc dữ liệu đơn giản . Sẽ khó xử lý nếu dữ liệu thuộc loại tùy chỉnh hoặc có cấu trúc không nằm trong cây hoặc danh sách (ví dụ: biểu đồ). Trong hầu hết các trường hợp, danh sách là đủ và thậm chí trong một số trường hợp, một mô hình chỉ nên chứa một mục nhập duy nhất. Đặc biệt nếu bạn muốn lập mô hình một mục nhập duy nhất có các thuộc tính khác nhau (một thể hiện của một lớp), thì khung mô hình / khung nhìn của Qt không phải là cách phù hợp để tách logic khỏi giao diện người dùng.
Tóm lại, tôi nghĩ rằng mô hình / khung xem của Qt hữu ích nếu và chỉ khi dữ liệu của bạn đang được xem bởi một trong các tiện ích người xem của Qt . Hoàn toàn vô ích nếu bạn sắp viết trình xem của riêng mình cho một mô hình chỉ chứa một mục nhập, ví dụ như cài đặt ứng dụng của bạn hoặc nếu dữ liệu của bạn không thuộc loại có thể in được.
Tôi đã sử dụng mô hình / chế độ xem Qt trong một ứng dụng (lớn hơn) như thế nào?
Tôi đã từng viết (trong một nhóm) một ứng dụng sử dụng nhiều mô hình Qt để quản lý dữ liệu. Chúng tôi quyết định tạo một DataRole
để giữ dữ liệu thực tế thuộc loại tùy chỉnh khác nhau cho từng lớp con của mô hình khác nhau. Chúng tôi đã tạo một lớp mô hình bên ngoài được gọi là Model
giữ tất cả các mô hình Qt khác nhau. Chúng tôi cũng tạo một lớp khung nhìn bên ngoài được gọi là View
giữ các cửa sổ (widget) được kết nối với các mô hình bên trong Model
. Vì vậy, cách tiếp cận này là một Qt MVC mở rộng, được điều chỉnh cho phù hợp với nhu cầu của chúng ta. Bản thân cả hai Model
và View
các lớp không liên quan gì đến Qt MVC.
Chúng ta đã đặt logic ở đâu? Chúng tôi đã tạo các lớp thực hiện tính toán thực tế trên dữ liệu bằng cách đọc dữ liệu từ các mô hình nguồn (khi chúng thay đổi) và ghi kết quả vào các mô hình đích. Theo quan điểm của Qt, các lớp logic này sẽ là các khung nhìn, vì chúng "kết nối" với các mô hình (không phải "chế độ xem" cho người dùng, mà là một "chế độ xem" cho phần logic nghiệp vụ của ứng dụng).
Bộ điều khiển ở đâu? Trong thuật ngữ MVC ban đầu, bộ điều khiển diễn giải đầu vào của người dùng (chuột và bàn phím) và đưa ra các lệnh cho mô hình để thực hiện hành động được yêu cầu. Vì chế độ xem Qt đã diễn giải thông tin đầu vào của người dùng như đổi tên và di chuyển các mục, điều này không cần thiết. Nhưng những gì chúng tôi cần là diễn giải về tương tác của người dùng vượt ra ngoài quan điểm Qt.