Skip to content

Commit

Permalink
Inline creation of text provider in hyperlink
Browse files Browse the repository at this point in the history
  • Loading branch information
Jacalz committed Feb 1, 2024
1 parent aa90b3d commit 2dba262
Show file tree
Hide file tree
Showing 3 changed files with 13 additions and 37 deletions.
33 changes: 5 additions & 28 deletions widget/hyperlink.go
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,7 @@ type Hyperlink struct {

textSize fyne.Size // updated in syncSegments
focused, hovered bool
provider *RichText
provider RichText
}

// NewHyperlink creates a new hyperlink widget with the set text content
Expand All @@ -58,8 +58,7 @@ func NewHyperlinkWithStyle(text string, url *url.URL, alignment fyne.TextAlign,
// CreateRenderer is a private method to Fyne which links this widget to its renderer
func (hl *Hyperlink) CreateRenderer() fyne.WidgetRenderer {
hl.ExtendBaseWidget(hl)
hl.provider = NewRichTextWithText(hl.Text)
hl.provider.ExtendBaseWidget(hl.provider)
hl.provider.ExtendBaseWidget(&hl.provider)
hl.syncSegments()

focus := canvas.NewRectangle(color.Transparent)
Expand All @@ -68,7 +67,7 @@ func (hl *Hyperlink) CreateRenderer() fyne.WidgetRenderer {
focus.Hide()
under := canvas.NewRectangle(theme.HyperlinkColor())
under.Hide()
return &hyperlinkRenderer{hl: hl, objects: []fyne.CanvasObject{hl.provider, focus, under}, focus: focus, under: under}
return &hyperlinkRenderer{hl: hl, objects: []fyne.CanvasObject{&hl.provider, focus, under}, focus: focus, under: under}
}

// Cursor returns the cursor type of this widget
Expand Down Expand Up @@ -135,11 +134,7 @@ func (hl *Hyperlink) focusXPos() float32 {
func (hl *Hyperlink) isPosOverText(pos fyne.Position) bool {
innerPad := theme.InnerPadding()
pad := theme.Padding()
// If not rendered yet provider will be nil
lineCount := float32(1)
if hl.provider != nil {
lineCount = fyne.Max(lineCount, float32(len(hl.provider.rowBounds)))
}
lineCount := fyne.Max(1, float32(len(hl.provider.rowBounds)))

xpos := hl.focusXPos()
return pos.X >= xpos && pos.X <= xpos+hl.focusWidth() &&
Expand All @@ -150,40 +145,27 @@ func (hl *Hyperlink) isPosOverText(pos fyne.Position) bool {
//
// Implements: fyne.Widget
func (hl *Hyperlink) Refresh() {
if hl.provider == nil { // not created until visible
return
}
hl.syncSegments()

hl.provider.Refresh()
hl.BaseWidget.Refresh()
}

// MinSize returns the smallest size this widget can shrink to
func (hl *Hyperlink) MinSize() fyne.Size {
if hl.provider == nil {
hl.CreateRenderer()
}

hl.syncSegments()
return hl.provider.MinSize()
}

// Resize sets a new size for the hyperlink.
// Note this should not be used if the widget is being managed by a Layout within a Container.
func (hl *Hyperlink) Resize(size fyne.Size) {
hl.BaseWidget.Resize(size)
if hl.provider == nil { // not created until visible
return
}
hl.provider.Resize(size)
}

// SetText sets the text of the hyperlink
func (hl *Hyperlink) SetText(text string) {
hl.Text = text
if hl.provider == nil { // not created until visible
return
}
hl.syncSegments()
hl.provider.Refresh()
}
Expand All @@ -205,11 +187,6 @@ func (hl *Hyperlink) SetURLFromString(str string) error {

// Tapped is called when a pointer tapped event is captured and triggers any change handler
func (hl *Hyperlink) Tapped(e *fyne.PointEvent) {
// If not rendered yet (hl.provider == nil), register all taps
// in practice this probably only happens in our unit tests
if hl.provider != nil && !hl.isPosOverText(e.Position) {
return
}
hl.invokeAction()
}

Expand Down
6 changes: 3 additions & 3 deletions widget/hyperlink_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -50,7 +50,7 @@ func TestHyperlink_Cursor(t *testing.T) {
func TestHyperlink_Alignment(t *testing.T) {
hyperlink := &Hyperlink{Text: "Test", Alignment: fyne.TextAlignTrailing}
hyperlink.CreateRenderer()
assert.Equal(t, fyne.TextAlignTrailing, textRenderTexts(hyperlink.provider)[0].Alignment)
assert.Equal(t, fyne.TextAlignTrailing, textRenderTexts(&hyperlink.provider)[0].Alignment)
}

func TestHyperlink_Hide(t *testing.T) {
Expand Down Expand Up @@ -130,7 +130,7 @@ func TestHyperlink_SetText(t *testing.T) {
hyperlink.SetText("New")

assert.Equal(t, "New", hyperlink.Text)
assert.Equal(t, "New", textRenderTexts(hyperlink.provider)[0].Text)
assert.Equal(t, "New", textRenderTexts(&hyperlink.provider)[0].Text)
}

func TestHyperlink_SetUrl(t *testing.T) {
Expand All @@ -153,7 +153,7 @@ func TestHyperlink_Truncate(t *testing.T) {
hyperlink.CreateRenderer()
hyperlink.Resize(fyne.NewSize(100, 20))

r := test.WidgetRenderer(hyperlink.provider)
r := test.WidgetRenderer(&hyperlink.provider)
assert.Equal(t, "TestingWithLongText", r.Objects()[0].(*canvas.Text).Text)

hyperlink.Truncation = fyne.TextTruncateClip
Expand Down
11 changes: 5 additions & 6 deletions widget/richtext_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -379,14 +379,13 @@ func TestTextRenderer_ApplyTheme(t *testing.T) {
func TestTextProvider_LineSizeToColumn(t *testing.T) {
label := NewLabel("Test")
label.CreateRenderer() // TODO make this a simple refresh call once it's in
provider := label.provider

fullSize := provider.lineSizeToColumn(4, 0)
assert.Equal(t, fullSize, provider.lineSizeToColumn(10, 0))
assert.Greater(t, fullSize.Width, provider.lineSizeToColumn(2, 0).Width)
fullSize := label.provider.lineSizeToColumn(4, 0)
assert.Equal(t, fullSize, label.provider.lineSizeToColumn(10, 0))
assert.Greater(t, fullSize.Width, label.provider.lineSizeToColumn(2, 0).Width)

out := provider.lineSizeToColumn(-1, -1)
assert.Equal(t, out, provider.lineSizeToColumn(0, 0))
out := label.provider.lineSizeToColumn(-1, -1)
assert.Equal(t, out, label.provider.lineSizeToColumn(0, 0))
}

func TestText_splitLines(t *testing.T) {
Expand Down

0 comments on commit 2dba262

Please sign in to comment.