1df06e3f39
- Use htmx to perform the button request - `hx-headers='{"x-csrf-token": "{{.CsrfToken}}"}'` to authenticate (we should probably learn to reuse this) - `hx-post="{{.ContextUser.HomeLink}}?action=follow"` to send a POST request to follow the user - `hx-target="#profile-avatar-card"` to target the card div for replacement - `hx-swap="outerHTML"` to replace the card (as opposed to its inner content) with the new card that shows the new follower count and button color - Change the backend response to return a `<div>` tag (the card) instead of a redirect to the user page # Before ![before](https://github.com/go-gitea/gitea/assets/20454870/86899d15-41c9-42ed-bd85-253b9caac7f8) # After ![after](https://github.com/go-gitea/gitea/assets/20454870/59455d96-548c-4a81-a5b0-fab1dc1e87ef) Signed-off-by: Yarden Shoham <git@yardenshoham.com>
127 lines
4.8 KiB
Handlebars
127 lines
4.8 KiB
Handlebars
<div id="profile-avatar-card" class="ui card">
|
|
<div id="profile-avatar" class="content gt-df">
|
|
{{if eq .SignedUserID .ContextUser.ID}}
|
|
<a class="image" href="{{AppSubUrl}}/user/settings" data-tooltip-content="{{ctx.Locale.Tr "user.change_avatar"}}">
|
|
{{/* the size doesn't take affect (and no need to take affect), image size(width) should be controlled by the parent container since this is not a flex layout*/}}
|
|
{{ctx.AvatarUtils.Avatar .ContextUser 256}}
|
|
</a>
|
|
{{else}}
|
|
<span class="image">
|
|
{{ctx.AvatarUtils.Avatar .ContextUser 256}}
|
|
</span>
|
|
{{end}}
|
|
</div>
|
|
<div class="content gt-word-break profile-avatar-name">
|
|
{{if .ContextUser.FullName}}<span class="header text center">{{.ContextUser.FullName}}</span>{{end}}
|
|
<span class="username text center">{{.ContextUser.Name}} {{if .IsAdmin}}
|
|
<a class="muted" href="{{AppSubUrl}}/admin/users/{{.ContextUser.ID}}" data-tooltip-content="{{ctx.Locale.Tr "admin.users.details"}}">
|
|
{{svg "octicon-gear" 18}}
|
|
</a>
|
|
{{end}}</span>
|
|
<div class="gt-mt-3">
|
|
<a class="muted" href="{{.ContextUser.HomeLink}}?tab=followers">{{svg "octicon-person" 18 "gt-mr-2"}}{{.NumFollowers}} {{ctx.Locale.Tr "user.followers"}}</a> · <a class="muted" href="{{.ContextUser.HomeLink}}?tab=following">{{.NumFollowing}} {{ctx.Locale.Tr "user.following"}}</a>
|
|
{{if .EnableFeed}}
|
|
<a href="{{.ContextUser.HomeLink}}.rss"><i class="ui text grey gt-ml-3" data-tooltip-content="{{ctx.Locale.Tr "rss_feed"}}">{{svg "octicon-rss" 18}}</i></a>
|
|
{{end}}
|
|
</div>
|
|
</div>
|
|
<div class="extra content gt-word-break">
|
|
<ul>
|
|
{{if .ContextUser.Location}}
|
|
<li>
|
|
{{svg "octicon-location"}}
|
|
<span class="gt-f1">{{.ContextUser.Location}}</span>
|
|
{{if .UserLocationMapURL}}
|
|
{{/* We presume that the UserLocationMapURL is safe, as it is provided by the site administrator. */}}
|
|
<a href="{{.UserLocationMapURL | Safe}}{{.ContextUser.Location | QueryEscape}}" rel="nofollow noreferrer" data-tooltip-content="{{ctx.Locale.Tr "user.show_on_map"}}">
|
|
{{svg "octicon-link-external"}}
|
|
</a>
|
|
{{end}}
|
|
</li>
|
|
{{end}}
|
|
{{if (eq .SignedUserID .ContextUser.ID)}}
|
|
<li>
|
|
{{svg "octicon-mail"}}
|
|
<a class="gt-f1" href="mailto:{{.ContextUser.Email}}" rel="nofollow">{{.ContextUser.Email}}</a>
|
|
<a href="{{AppSubUrl}}/user/settings#privacy-user-settings">
|
|
{{if .ShowUserEmail}}
|
|
<i data-tooltip-content="{{ctx.Locale.Tr "user.email_visibility.limited"}}">
|
|
{{svg "octicon-unlock"}}
|
|
</i>
|
|
{{else}}
|
|
<i data-tooltip-content="{{ctx.Locale.Tr "user.email_visibility.private"}}">
|
|
{{svg "octicon-lock"}}
|
|
</i>
|
|
{{end}}
|
|
</a>
|
|
</li>
|
|
{{else}}
|
|
{{if .ShowUserEmail}}
|
|
<li>
|
|
{{svg "octicon-mail"}}
|
|
<a href="mailto:{{.ContextUser.Email}}" rel="nofollow">{{.ContextUser.Email}}</a>
|
|
</li>
|
|
{{end}}
|
|
{{end}}
|
|
{{if .ContextUser.Website}}
|
|
<li>
|
|
{{svg "octicon-link"}}
|
|
<a target="_blank" rel="noopener noreferrer me" href="{{.ContextUser.Website}}">{{.ContextUser.Website}}</a>
|
|
</li>
|
|
{{end}}
|
|
{{if $.RenderedDescription}}
|
|
<li>
|
|
<div class="render-content markup">{{$.RenderedDescription|Str2html}}</div>
|
|
</li>
|
|
{{end}}
|
|
{{range .OpenIDs}}
|
|
{{if .Show}}
|
|
<li>
|
|
{{svg "fontawesome-openid"}}
|
|
<a target="_blank" rel="noopener noreferrer" href="{{.URI}}">{{.URI}}</a>
|
|
</li>
|
|
{{end}}
|
|
{{end}}
|
|
<li>{{svg "octicon-calendar"}} <span>{{ctx.Locale.Tr "user.joined_on" (DateTime "short" .ContextUser.CreatedUnix) | Safe}}</span></li>
|
|
{{if and .Orgs .HasOrgsVisible}}
|
|
<li>
|
|
<ul class="user-orgs">
|
|
{{range .Orgs}}
|
|
{{if (or .Visibility.IsPublic (and ($.SignedUser) (or .Visibility.IsLimited (and (.HasMemberWithUserID ctx $.SignedUserID) .Visibility.IsPrivate) ($.IsAdmin))))}}
|
|
<li>
|
|
<a href="{{.HomeLink}}" data-tooltip-content="{{.Name}}">
|
|
{{ctx.AvatarUtils.Avatar .}}
|
|
</a>
|
|
</li>
|
|
{{end}}
|
|
{{end}}
|
|
</ul>
|
|
</li>
|
|
{{end}}
|
|
{{if .Badges}}
|
|
<li>
|
|
<ul class="user-badges">
|
|
{{range .Badges}}
|
|
<li>
|
|
<img width="64" height="64" src="{{.ImageURL}}" alt="{{.Description}}" data-tooltip-content="{{.Description}}">
|
|
</li>
|
|
{{end}}
|
|
</ul>
|
|
</li>
|
|
{{end}}
|
|
{{if and .IsSigned (ne .SignedUserID .ContextUser.ID)}}
|
|
<li class="follow" hx-headers='{"x-csrf-token": "{{.CsrfToken}}"}' hx-target="#profile-avatar-card" hx-swap="outerHTML">
|
|
{{if $.IsFollowing}}
|
|
<button hx-post="{{.ContextUser.HomeLink}}?action=unfollow" class="ui basic red button">
|
|
{{svg "octicon-person"}} {{ctx.Locale.Tr "user.unfollow"}}
|
|
</button>
|
|
{{else}}
|
|
<button hx-post="{{.ContextUser.HomeLink}}?action=follow" class="ui basic primary button">
|
|
{{svg "octicon-person"}} {{ctx.Locale.Tr "user.follow"}}
|
|
</button>
|
|
{{end}}
|
|
</li>
|
|
{{end}}
|
|
</ul>
|
|
</div>
|
|
</div>
|