github.com/wtfutil/wtf@v0.43.0/modules/gitlab/widget.go (about) 1 package gitlab 2 3 import ( 4 "strconv" 5 6 "github.com/rivo/tview" 7 "github.com/wtfutil/wtf/utils" 8 "github.com/wtfutil/wtf/view" 9 ) 10 11 type ContentItem struct { 12 Type string 13 ID int 14 } 15 16 type Widget struct { 17 view.MultiSourceWidget 18 view.TextWidget 19 20 GitlabProjects []*GitlabProject 21 22 context *context 23 settings *Settings 24 Selected int 25 maxItems int 26 Items []ContentItem 27 28 configError error 29 } 30 31 // NewWidget creates a new instance of the widget 32 func NewWidget(tviewApp *tview.Application, redrawChan chan bool, pages *tview.Pages, settings *Settings) *Widget { 33 context, err := newContext(settings) 34 35 widget := Widget{ 36 MultiSourceWidget: view.NewMultiSourceWidget(settings.Common, "project", "projects"), 37 TextWidget: view.NewTextWidget(tviewApp, redrawChan, pages, settings.Common), 38 39 context: context, 40 settings: settings, 41 42 configError: err, 43 } 44 45 widget.GitlabProjects = widget.buildProjectCollection(context, settings.projects) 46 47 widget.initializeKeyboardControls() 48 widget.View.SetRegions(true) 49 widget.SetDisplayFunction(widget.display) 50 51 widget.Unselect() 52 53 return &widget 54 } 55 56 /* -------------------- Exported Functions -------------------- */ 57 58 func (widget *Widget) Refresh() { 59 if widget.context == nil || widget.configError != nil { 60 widget.displayError() 61 return 62 } 63 64 for _, project := range widget.GitlabProjects { 65 project.Refresh() 66 } 67 68 widget.display() 69 } 70 71 // SetItemCount sets the amount of PRs RRs and other PRs throughout the widgets display creation 72 func (widget *Widget) SetItemCount(items int) { 73 widget.maxItems = items 74 } 75 76 // GetItemCount returns the amount of PRs RRs and other PRs calculated so far as an int 77 func (widget *Widget) GetItemCount() int { 78 return widget.maxItems 79 } 80 81 // GetSelected returns the index of the currently highlighted item as an int 82 func (widget *Widget) GetSelected() int { 83 if widget.Selected < 0 { 84 return 0 85 } 86 return widget.Selected 87 } 88 89 // Next cycles the currently highlighted text down 90 func (widget *Widget) Next() { 91 widget.Selected++ 92 if widget.Selected >= widget.maxItems { 93 widget.Selected = 0 94 } 95 widget.View.Highlight(strconv.Itoa(widget.Selected)) 96 widget.View.ScrollToHighlight() 97 } 98 99 // Prev cycles the currently highlighted text up 100 func (widget *Widget) Prev() { 101 widget.Selected-- 102 if widget.Selected < 0 { 103 widget.Selected = widget.maxItems - 1 104 } 105 widget.View.Highlight(strconv.Itoa(widget.Selected)) 106 widget.View.ScrollToHighlight() 107 } 108 109 // Unselect stops highlighting the text and jumps the scroll position to the top 110 func (widget *Widget) Unselect() { 111 widget.Selected = -1 112 widget.View.Highlight() 113 widget.View.ScrollToBeginning() 114 } 115 116 /* -------------------- Unexported Functions -------------------- */ 117 118 func (widget *Widget) buildProjectCollection(context *context, projectData []string) []*GitlabProject { 119 gitlabProjects := []*GitlabProject{} 120 121 for _, projectPath := range projectData { 122 project := NewGitlabProject(context, projectPath) 123 gitlabProjects = append(gitlabProjects, project) 124 } 125 126 return gitlabProjects 127 } 128 129 func (widget *Widget) currentGitlabProject() *GitlabProject { 130 if len(widget.GitlabProjects) == 0 { 131 return nil 132 } 133 134 if widget.Idx < 0 || widget.Idx >= len(widget.GitlabProjects) { 135 return nil 136 } 137 138 return widget.GitlabProjects[widget.Idx] 139 } 140 141 func (widget *Widget) openItemInBrowser() { 142 currentSelection := widget.View.GetHighlights() 143 if widget.Selected >= 0 && currentSelection[0] != "" { 144 145 item := widget.Items[widget.Selected] 146 url := "" 147 148 project := widget.currentGitlabProject() 149 if project == nil { 150 // This is a problem. We will just bail out for now 151 return 152 } 153 154 switch item.Type { 155 case "MR": 156 url = (project.RemoteProject.WebURL + "/merge_requests/" + strconv.Itoa(item.ID)) 157 case "ISSUE": 158 url = (project.RemoteProject.WebURL + "/issues/" + strconv.Itoa(item.ID)) 159 } 160 161 utils.OpenFile(url) 162 } 163 } 164 165 func (widget *Widget) openRepo() { 166 project := widget.currentGitlabProject() 167 if project == nil { 168 return 169 } 170 url := project.RemoteProject.WebURL 171 utils.OpenFile(url) 172 } 173 174 func (widget *Widget) openPulls() { 175 project := widget.currentGitlabProject() 176 if project == nil { 177 return 178 } 179 url := project.RemoteProject.WebURL + "/merge_requests/" 180 utils.OpenFile(url) 181 } 182 183 func (widget *Widget) openIssues() { 184 project := widget.currentGitlabProject() 185 if project == nil { 186 return 187 } 188 url := project.RemoteProject.WebURL + "/issues/" 189 utils.OpenFile(url) 190 }