mirror of
https://github.com/discourse/discourse.git
synced 2024-11-23 13:03:45 +08:00
UX: Reduce number of links displayed in Community by default (#17703)
Additional links are hidden by default and can be accessed via the "more..." link.
This commit is contained in:
parent
988a175e94
commit
9efeaf2ae3
|
@ -12,18 +12,26 @@ import UsersSectionLink from "discourse/lib/sidebar/community-section/users-sect
|
|||
import { action } from "@ember/object";
|
||||
import { next } from "@ember/runloop";
|
||||
|
||||
const DEFAULT_SECTION_LINKS = [
|
||||
const MAIN_SECTION_LINKS = [
|
||||
EverythingSectionLink,
|
||||
TrackedSectionLink,
|
||||
GroupsSectionLink,
|
||||
UsersSectionLink,
|
||||
MyPostsSectionLink,
|
||||
];
|
||||
|
||||
export default class SidebarCommunitySection extends GlimmerComponent {
|
||||
configuredSectionLinks = [...DEFAULT_SECTION_LINKS, ...customSectionLinks];
|
||||
const MORE_SECTION_LINKS = [GroupsSectionLink, UsersSectionLink];
|
||||
|
||||
sectionLinks = this.configuredSectionLinks.map((sectionLinkClass) => {
|
||||
export default class SidebarCommunitySection extends GlimmerComponent {
|
||||
moreSectionLinks = [...MORE_SECTION_LINKS, ...customSectionLinks].map(
|
||||
(sectionLinkClass) => {
|
||||
return new sectionLinkClass({
|
||||
topicTrackingState: this.topicTrackingState,
|
||||
currentUser: this.currentUser,
|
||||
appEvents: this.appEvents,
|
||||
});
|
||||
}
|
||||
);
|
||||
|
||||
sectionLinks = MAIN_SECTION_LINKS.map((sectionLinkClass) => {
|
||||
return new sectionLinkClass({
|
||||
topicTrackingState: this.topicTrackingState,
|
||||
currentUser: this.currentUser,
|
||||
|
|
|
@ -0,0 +1,92 @@
|
|||
import { tracked } from "@glimmer/tracking";
|
||||
import { action } from "@ember/object";
|
||||
import { inject as service } from "@ember/service";
|
||||
import { bind } from "discourse-common/utils/decorators";
|
||||
import GlimmerComponent from "discourse/components/glimmer";
|
||||
|
||||
export default class SidebarMoreSectionLinks extends GlimmerComponent {
|
||||
@tracked shouldDisplaySectionLinks = false;
|
||||
@tracked activeSectionLink;
|
||||
@service router;
|
||||
|
||||
constructor() {
|
||||
super(...arguments);
|
||||
this.#setActiveSectionLink();
|
||||
this.router.on("routeDidChange", this, this.#setActiveSectionLink);
|
||||
}
|
||||
|
||||
willDestroy() {
|
||||
this.#removeClickEventListener();
|
||||
this.router.off("routeDidChange", this, this.#setActiveSectionLink);
|
||||
}
|
||||
|
||||
get sectionLinks() {
|
||||
if (this.activeSectionLink) {
|
||||
return this.args.sectionLinks.filter((sectionLink) => {
|
||||
return sectionLink.name !== this.activeSectionLink.name;
|
||||
});
|
||||
} else {
|
||||
return this.args.sectionLinks;
|
||||
}
|
||||
}
|
||||
|
||||
@bind
|
||||
closeDetails(event) {
|
||||
if (this.shouldDisplaySectionLinks) {
|
||||
const isLinkClick = event.target.className.includes(
|
||||
"sidebar-section-link"
|
||||
);
|
||||
|
||||
if (isLinkClick || this.#isOutsideDetailsClick(event)) {
|
||||
document
|
||||
.querySelector(".sidebar-more-section-links-details")
|
||||
?.removeAttribute("open");
|
||||
|
||||
this.toggleSectionLinks();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@action
|
||||
registerClickListener() {
|
||||
this.#addClickEventListener();
|
||||
}
|
||||
|
||||
@action
|
||||
unregisterClickListener() {
|
||||
this.#removeClickEventListener();
|
||||
}
|
||||
|
||||
@action
|
||||
toggleSectionLinks() {
|
||||
this.shouldDisplaySectionLinks = !this.shouldDisplaySectionLinks;
|
||||
}
|
||||
|
||||
#removeClickEventListener() {
|
||||
document.removeEventListener("click", this.closeDetails);
|
||||
}
|
||||
|
||||
#addClickEventListener() {
|
||||
document.addEventListener("click", this.closeDetails);
|
||||
}
|
||||
|
||||
#isOutsideDetailsClick(event) {
|
||||
return !event.composedPath().some((element) => {
|
||||
return element.className === "sidebar-more-section-links-details";
|
||||
});
|
||||
}
|
||||
|
||||
#setActiveSectionLink() {
|
||||
const activeSectionLink = this.args.sectionLinks.find((sectionLink) => {
|
||||
const args = [sectionLink.route];
|
||||
|
||||
if (sectionLink.model) {
|
||||
args.push(sectionLink.model);
|
||||
}
|
||||
|
||||
return this.router.isActive(...args) && sectionLink;
|
||||
});
|
||||
|
||||
this.activeSectionLink = activeSectionLink;
|
||||
}
|
||||
}
|
|
@ -19,4 +19,6 @@
|
|||
@badgeText={{sectionLink.badgeText}}
|
||||
@model={{sectionLink.model}} />
|
||||
{{/each}}
|
||||
|
||||
<Sidebar::MoreSectionLinks @sectionLinks={{this.moreSectionLinks}} />
|
||||
</Sidebar::Section>
|
||||
|
|
|
@ -0,0 +1,36 @@
|
|||
{{#if this.activeSectionLink}}
|
||||
<Sidebar::SectionLink
|
||||
@linkName={{this.activeSectionLink.name}}
|
||||
@route={{this.activeSectionLink.route}}
|
||||
@query={{this.activeSectionLink.query}}
|
||||
@title={{this.activeSectionLink.title}}
|
||||
@content={{this.activeSectionLink.text}}
|
||||
@currentWhen={{this.activeSectionLink.currentWhen}}
|
||||
@badgeText={{this.activeSectionLink.badgeText}}
|
||||
@model={{this.activeSectionLink.model}} />
|
||||
{{/if}}
|
||||
|
||||
<details class="sidebar-more-section-links-details" {{on "click" this.toggleSectionLinks}}>
|
||||
<summary class="sidebar-more-section-links-details-summary" >
|
||||
{{i18n "sidebar.more_count" (hash count=this.sectionLinks.length)}}
|
||||
</summary>
|
||||
|
||||
{{#if this.shouldDisplaySectionLinks}}
|
||||
<div class="sidebar-more-section-links-details-content"
|
||||
{{did-insert this.registerClickListener}}
|
||||
{{will-destroy this.unregisterClickListener}} >
|
||||
|
||||
{{#each this.sectionLinks as |sectionLink|}}
|
||||
<Sidebar::SectionLink
|
||||
@linkName={{sectionLink.name}}
|
||||
@route={{sectionLink.route}}
|
||||
@query={{sectionLink.query}}
|
||||
@title={{sectionLink.title}}
|
||||
@content={{sectionLink.text}}
|
||||
@currentWhen={{sectionLink.currentWhen}}
|
||||
@badgeText={{sectionLink.badgeText}}
|
||||
@model={{sectionLink.model}} />
|
||||
{{/each}}
|
||||
</div>
|
||||
{{/if}}
|
||||
</details>
|
|
@ -114,6 +114,45 @@ acceptance("Sidebar - Community Section", function (needs) {
|
|||
);
|
||||
});
|
||||
|
||||
test("clicking on more... link", async function (assert) {
|
||||
await visit("/");
|
||||
|
||||
await click(
|
||||
".sidebar-section-community .sidebar-more-section-links-details-summary"
|
||||
);
|
||||
|
||||
assert.ok(
|
||||
exists(
|
||||
".sidebar-section-community .sidebar-more-section-links-details-content"
|
||||
),
|
||||
"additional section links are displayed"
|
||||
);
|
||||
|
||||
await click(
|
||||
".sidebar-section-community .sidebar-more-section-links-details-summary"
|
||||
);
|
||||
|
||||
assert.notOk(
|
||||
exists(
|
||||
".sidebar-section-community .sidebar-more-section-links-details-content"
|
||||
),
|
||||
"additional section links are hidden"
|
||||
);
|
||||
|
||||
await click(
|
||||
".sidebar-section-community .sidebar-more-section-links-details-summary"
|
||||
);
|
||||
|
||||
await click("#main-outlet");
|
||||
|
||||
assert.notOk(
|
||||
exists(
|
||||
".sidebar-section-community .sidebar-more-section-links-details-content"
|
||||
),
|
||||
"additional section links are hidden when clicking outside"
|
||||
);
|
||||
});
|
||||
|
||||
test("clicking on everything link", async function (assert) {
|
||||
await visit("/t/280");
|
||||
await click(".sidebar-section-community .sidebar-section-link-everything");
|
||||
|
@ -162,6 +201,16 @@ acceptance("Sidebar - Community Section", function (needs) {
|
|||
|
||||
test("clicking on users link", async function (assert) {
|
||||
await visit("/t/280");
|
||||
|
||||
assert.notOk(
|
||||
exists(".sidebar-section-community .sidebar-section-link-users"),
|
||||
"users link is not displayed in sidebar when it is not the active route"
|
||||
);
|
||||
|
||||
await click(
|
||||
".sidebar-section-community .sidebar-more-section-links-details-summary"
|
||||
);
|
||||
|
||||
await click(".sidebar-section-community .sidebar-section-link-users");
|
||||
|
||||
assert.strictEqual(
|
||||
|
@ -180,10 +229,35 @@ acceptance("Sidebar - Community Section", function (needs) {
|
|||
exists(".sidebar-section-community .sidebar-section-link-users.active"),
|
||||
"the users link is marked as active"
|
||||
);
|
||||
|
||||
assert.strictEqual(
|
||||
query(
|
||||
".sidebar-section-community .sidebar-more-section-links-details-summary"
|
||||
).textContent.trim(),
|
||||
I18n.t("sidebar.more_count", { count: 1 }),
|
||||
"displays the right count as users link is currently active"
|
||||
);
|
||||
|
||||
await visit("/u");
|
||||
|
||||
assert.ok(
|
||||
exists(".sidebar-section-community .sidebar-section-link-users.active"),
|
||||
"users link is displayed in sidebar when it is the active route"
|
||||
);
|
||||
});
|
||||
|
||||
test("clicking on groups link", async function (assert) {
|
||||
await visit("/t/280");
|
||||
|
||||
assert.notOk(
|
||||
exists(".sidebar-section-community .sidebar-section-link-groups"),
|
||||
"groups link is not displayed in sidebar when it is not the active route"
|
||||
);
|
||||
|
||||
await click(
|
||||
".sidebar-section-community .sidebar-more-section-links-details-summary"
|
||||
);
|
||||
|
||||
await click(".sidebar-section-community .sidebar-section-link-groups");
|
||||
|
||||
assert.strictEqual(
|
||||
|
@ -202,6 +276,21 @@ acceptance("Sidebar - Community Section", function (needs) {
|
|||
exists(".sidebar-section-community .sidebar-section-link-groups.active"),
|
||||
"the groups link is marked as active"
|
||||
);
|
||||
|
||||
assert.strictEqual(
|
||||
query(
|
||||
".sidebar-section-community .sidebar-more-section-links-details-summary"
|
||||
).textContent.trim(),
|
||||
I18n.t("sidebar.more_count", { count: 1 }),
|
||||
"displays the right count as groups link is currently active"
|
||||
);
|
||||
|
||||
await visit("/g");
|
||||
|
||||
assert.ok(
|
||||
exists(".sidebar-section-community .sidebar-section-link-groups.active"),
|
||||
"groups link is displayed in sidebar when it is the active route"
|
||||
);
|
||||
});
|
||||
|
||||
test("clicking on my posts link", async function (assert) {
|
||||
|
@ -679,6 +768,10 @@ acceptance("Sidebar - Community Section", function (needs) {
|
|||
|
||||
await visit("/");
|
||||
|
||||
await click(
|
||||
".sidebar-section-community .sidebar-more-section-links-details-summary"
|
||||
);
|
||||
|
||||
assert.strictEqual(
|
||||
query(".sidebar-section-link-unread").textContent.trim(),
|
||||
"unread topics",
|
||||
|
@ -724,6 +817,11 @@ acceptance("Sidebar - Community Section", function (needs) {
|
|||
});
|
||||
|
||||
await visit("/");
|
||||
|
||||
await click(
|
||||
".sidebar-section-community .sidebar-more-section-links-details-summary"
|
||||
);
|
||||
|
||||
await click(".sidebar-section-link-user-summary");
|
||||
|
||||
assert.strictEqual(
|
||||
|
|
|
@ -47,6 +47,7 @@
|
|||
@import "sidebar";
|
||||
@import "sidebar-footer";
|
||||
@import "sidebar-section";
|
||||
@import "sidebar-more-section-links";
|
||||
@import "sidebar-section-link";
|
||||
@import "tagging";
|
||||
@import "tooltip";
|
||||
|
|
|
@ -0,0 +1,32 @@
|
|||
.sidebar-more-section-links-details {
|
||||
margin-left: 1.5em;
|
||||
|
||||
.sidebar-more-section-links-details-summary {
|
||||
padding: 0.35em 0.5em;
|
||||
color: var(--tertiary);
|
||||
font-size: var(--font-down-1);
|
||||
transition: background-color 0.25s;
|
||||
|
||||
&:hover {
|
||||
background: var(--d-sidebar-highlight-color);
|
||||
}
|
||||
|
||||
list-style: none;
|
||||
|
||||
&::before {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
.sidebar-more-section-links-details-content {
|
||||
position: absolute;
|
||||
background-color: var(--secondary);
|
||||
width: 100%;
|
||||
box-shadow: shadow("dropdown");
|
||||
z-index: z("base") + 1;
|
||||
|
||||
.sidebar-section-link-wrapper {
|
||||
margin-left: none;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -134,6 +134,8 @@
|
|||
}
|
||||
}
|
||||
|
||||
#main-outlet-wrapper .sidebar-section-link-wrapper {
|
||||
#main-outlet-wrapper
|
||||
.sidebar-section-link-wrapper:not(.sidebar-more-section-links-details-content
|
||||
.sidebar-section-link-wrapper) {
|
||||
margin-left: 1.5em;
|
||||
}
|
||||
|
|
|
@ -4077,6 +4077,7 @@ en:
|
|||
one: "%{count} new"
|
||||
other: "%{count} new"
|
||||
toggle_section: "toggle section"
|
||||
more_count: "%{count} more..."
|
||||
sections:
|
||||
messages:
|
||||
header_link_title: "personal messages"
|
||||
|
|
Loading…
Reference in New Issue
Block a user