Merge 24dd359228889440789ed7a66e272e3406f79e4a into 635a3050f1caa83babd8424059457e067190d282

This commit is contained in:
Alex Hughes 2025-03-17 15:56:17 +07:00 committed by GitHub
commit edb62f2e33
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
4 changed files with 318 additions and 0 deletions

View File

@ -0,0 +1,109 @@
package main
import (
"fmt"
qt "github.com/mappu/miqt/qt6"
"os"
)
func GetTreeView(parent *qt.QWidget) *qt.QTreeView {
treeView := qt.NewQTreeView(parent)
treeView.SetAlternatingRowColors(true)
treeView.SetSortingEnabled(true)
treeView.SetColumnWidth(0, 300)
treeView.SetContentsMargins(0, 0, 0, 0)
treeView.Header().SetDefaultSectionSize(200)
treeView.Header().SetStretchLastSection(true)
treeView.SetSelectionMode(qt.QAbstractItemView__ExtendedSelection)
return treeView
}
func PopulateData(rootItem *TreeItem) {
cellData := make([]*TreeCell, 0)
cellData = append(cellData, NewTreeCell(qt.DisplayRole, *qt.NewQVariant11("Big File")))
cellData = append(cellData, NewTreeCell(qt.DisplayRole, *qt.NewQVariant11("10.7 MiB")))
item := NewTreeItem(cellData, rootItem, false)
err := item.SetData(1, qt.NewQVariant6(11225400), qt.UserRole)
if err != nil {
fmt.Printf("Error setting UserData: %v\n", err)
}
err = item.SetData(0, qt.NewQVariant11("Big File"), qt.UserRole)
if err != nil {
fmt.Printf("Error setting UserData: %v\n", err)
}
rootItem.AppendChild(&item)
cellData2 := make([]*TreeCell, 0)
cellData2 = append(cellData2, NewTreeCell(qt.DisplayRole, *qt.NewQVariant11("Small File")))
cellData2 = append(cellData2, NewTreeCell(qt.DisplayRole, *qt.NewQVariant11("110 Bytes")))
item2 := NewTreeItem(cellData2, rootItem, false)
err = item2.SetData(1, qt.NewQVariant6(110), qt.UserRole)
if err != nil {
fmt.Printf("Error setting UserData: %v\n", err)
}
err = item.SetData(0, qt.NewQVariant11("Small File"), qt.UserRole)
if err != nil {
fmt.Printf("Error setting UserData: %v\n", err)
}
rootItem.AppendChild(&item2)
cellData3 := make([]*TreeCell, 0)
cellData3 = append(cellData3, NewTreeCell(qt.DisplayRole, *qt.NewQVariant11("Medium File")))
cellData3 = append(cellData3, NewTreeCell(qt.DisplayRole, *qt.NewQVariant11("109.5 KiB")))
item3 := NewTreeItem(cellData3, rootItem, false)
err = item3.SetData(1, qt.NewQVariant6(112200), qt.UserRole)
if err != nil {
fmt.Printf("Error setting UserData: %v\n", err)
}
err = item.SetData(0, qt.NewQVariant11("Medium File"), qt.UserRole)
if err != nil {
fmt.Printf("Error setting UserData: %v\n", err)
}
rootItem.AppendChild(&item3)
}
func GetDialog() *qt.QDialog {
dialog := qt.NewQDialog3(nil, qt.Dialog)
dialog.SetWindowFlags(qt.WindowStaysOnTopHint)
dialogLayout := qt.NewQVBoxLayout2()
dialogLayout.SetSpacing(0)
dialogLayout.SetContentsMargins(0, 0, 0, 0)
dialog.SetContentsMargins(10, 10, 10, 10)
dialog.SetLayout(dialogLayout.Layout())
dialog.SetWindowTitle("Example Sort Model Usage")
treeView := GetTreeView(dialog.QWidget)
// Model
model, rootItem := GetModel(dialog.QObject)
PopulateData(rootItem)
sortModel := qt.NewQSortFilterProxyModel2(treeView.QObject)
sortModel.SetSortRole(int(qt.UserRole))
sortModel.OnLessThan(func(super func(source_left *qt.QModelIndex, source_right *qt.QModelIndex) bool, source_left *qt.QModelIndex, source_right *qt.QModelIndex) bool {
// In our case we know that the data from our TreeItem will come back as an int for our UserRole
leftData := sortModel.SourceModel().Data(source_left, sortModel.SortRole())
rightData := sortModel.SourceModel().Data(source_right, sortModel.SortRole())
if source_left.Column() == 0 {
return leftData.ToString() < rightData.ToString()
}
return leftData.ToLongLong() < rightData.ToLongLong()
})
sortModel.SetSourceModel(model)
treeView.SetModel(sortModel.QAbstractItemModel)
dialogLayout.AddWidget3(treeView.QWidget, 0, qt.AlignCenter)
return dialog
}
func main() {
qt.NewQApplication(os.Args)
dialog := GetDialog()
dialog.Show()
qt.QApplication_Exec()
}

View File

@ -0,0 +1,94 @@
package main
import (
qt "github.com/mappu/miqt/qt6"
"slices"
"unsafe"
)
func GetModel(parent *qt.QObject) (*qt.QAbstractItemModel, *TreeItem) {
model := qt.NewQAbstractItemModel2(parent)
data := make([]*TreeCell, 0)
data = append(data, NewTreeCell(qt.DisplayRole, *qt.NewQVariant11("Name")))
data = append(data, NewTreeCell(qt.DisplayRole, *qt.NewQVariant11("Size")))
rootItem := NewTreeItem(data, nil, true)
model.OnData(func(index *qt.QModelIndex, role int) *qt.QVariant {
if !index.IsValid() {
return qt.NewQVariant()
}
if !slices.Contains([]qt.ItemDataRole{qt.DisplayRole, qt.UserRole}, qt.ItemDataRole(role)) {
return qt.NewQVariant()
}
item := (*TreeItem)(index.InternalPointer())
return item.Data(index.Column(), qt.ItemDataRole(role))
})
model.OnHeaderData(func(super func(section int, orientation qt.Orientation, role int) *qt.QVariant, section int, orientation qt.Orientation, role int) *qt.QVariant {
if qt.ItemDataRole(role) != qt.DisplayRole {
return qt.NewQVariant()
}
if orientation == qt.Horizontal && role == int(qt.DisplayRole) {
return rootItem.Data(section, qt.DisplayRole)
}
return qt.NewQVariant()
})
model.OnIndex(func(row int, column int, parent *qt.QModelIndex) *qt.QModelIndex {
if !model.HasIndex3(row, column, parent) {
return qt.NewQModelIndex()
}
var parentItem *TreeItem
if !parent.IsValid() {
parentItem = &rootItem
} else {
parentItem = (*TreeItem)(parent.InternalPointer())
}
child, err := parentItem.Child(row)
if err != nil {
return qt.NewQModelIndex()
}
newIndex := model.CreateIndex2(row, column, uintptr(unsafe.Pointer(child)))
return &newIndex
})
model.OnParent(func(child *qt.QModelIndex) *qt.QModelIndex {
if !child.IsValid() {
return qt.NewQModelIndex()
}
parentItem := (*TreeItem)(child.InternalPointer()).ParentItem()
if parentItem != &rootItem {
row, err := parentItem.Row()
if err != nil {
return qt.NewQModelIndex()
}
index := model.CreateIndex2(row, 0, uintptr(unsafe.Pointer(parentItem)))
return &index
}
return qt.NewQModelIndex()
})
model.OnRowCount(func(parent *qt.QModelIndex) int {
if parent.Column() > 0 {
return 0
}
var item *TreeItem
if !parent.IsValid() {
item = &rootItem
} else {
item = (*TreeItem)(parent.InternalPointer())
}
return item.ChildCount()
})
model.OnColumnCount(func(parent *qt.QModelIndex) int {
if parent.IsValid() {
item := (*TreeItem)(parent.InternalPointer())
return item.ColumnCount()
}
return rootItem.ColumnCount()
})
return model, &rootItem
}

View File

@ -0,0 +1,33 @@
package main
import (
"fmt"
qt "github.com/mappu/miqt/qt6"
"strconv"
)
type TreeCell struct {
data map[qt.ItemDataRole]string
}
func NewTreeCell(role qt.ItemDataRole, value qt.QVariant) *TreeCell {
data := make(map[qt.ItemDataRole]string)
data[role] = value.ToString()
return &TreeCell{data: data}
}
func (cell *TreeCell) SetData(data qt.QVariant, role qt.ItemDataRole) {
cell.data[role] = data.ToString()
}
func (cell *TreeCell) Data(role qt.ItemDataRole) *qt.QVariant {
if role == qt.UserRole {
number, err := strconv.ParseInt(cell.data[role], 10, 64)
if err != nil {
fmt.Printf("Error converting %s to int: %v\n", number, err)
return qt.NewQVariant11(cell.data[role])
}
return qt.NewQVariant6(number)
}
return qt.NewQVariant11(cell.data[role])
}

View File

@ -0,0 +1,82 @@
package main
import (
"fmt"
"slices"
qt "github.com/mappu/miqt/qt6"
)
type TreeItem struct {
data []*TreeCell
parent *TreeItem
children []*TreeItem
isRoot bool
}
func NewTreeItem(data []*TreeCell, parent *TreeItem, isRoot bool) TreeItem {
return TreeItem{
data: data,
parent: parent,
isRoot: isRoot,
}
}
func (self *TreeItem) IsRoot() bool {
return self.isRoot
}
func (self *TreeItem) AppendChild(child *TreeItem) {
self.children = append(self.children, child)
}
func (self *TreeItem) Child(row int) (*TreeItem, error) {
if row >= 0 && row <= self.ChildCount() {
return self.children[row], nil
}
return nil, fmt.Errorf("TreeItem does not have child at row %d", row)
}
func (self *TreeItem) ColumnCount() int {
return len(self.data)
}
func (self *TreeItem) ChildCount() int {
return len(self.children)
}
func (self *TreeItem) Data(column int, role qt.ItemDataRole) *qt.QVariant {
if column >= 0 && column < len(self.data) {
if !slices.Contains([]qt.ItemDataRole{qt.DisplayRole, qt.UserRole}, role) {
return qt.NewQVariant()
}
return self.data[column].Data(role)
}
return qt.NewQVariant()
}
func (self *TreeItem) SetData(column int, value *qt.QVariant, role qt.ItemDataRole) error {
if column >= 0 && column < len(self.data) {
self.data[column].SetData(*value, role)
} else {
cell := NewTreeCell(role, *value)
self.data = append(self.data, cell)
}
return nil
}
func (self *TreeItem) Row() (int, error) {
if self.parent == nil {
return 0, nil
}
for index, child := range self.parent.children {
if child == self {
return index, nil
}
}
return 0, fmt.Errorf("could not find child in its parent")
}
func (self *TreeItem) ParentItem() *TreeItem {
return self.parent
}