mirror of
https://github.com/discourse/discourse.git
synced 2024-11-25 10:20:58 -06:00
FIX: limits max height to viewport on channel only (#21539)
Before this commit chat was applying a fixed height on everything under the `/chat` route. It's only really needed on the channel page with the composer at the bottom of the page. This commits makes the following changes: - moves height limitation from `#main-outlet-wrapper` to `.chat-channel` - makes browse channel page and members list page full height and rely on main document scrollbar - adds height computation for draft header and direct message creator block to ensure the height is correct when creating a draft channel - makes chat index full height to rely on the browser scrollbar. As a result the <kbd> + </kbd> button used on mobile to create a direct message as been moved out of `<ChannelsList>` into the chat index template - sidebar height was relying on chat setting a max height, as a result the height computation of sidebar has been changed to work correctly, especially with an opened keyboard on mobile or ipad
This commit is contained in:
parent
9a2780397f
commit
5ce0697348
@ -31,18 +31,21 @@
|
||||
|
||||
@include unselectable;
|
||||
|
||||
// 100dvh with fallback for old browsers
|
||||
--100dvh: 100vh;
|
||||
@supports (height: 100dvh) {
|
||||
--100dvh: 100dvh;
|
||||
// 1dvh with fallback for old browsers
|
||||
--1dvh: 1vh;
|
||||
@supports (height: 1dvh) {
|
||||
--1dvh: 1dvh;
|
||||
}
|
||||
|
||||
height: calc(var(--100dvh) - var(--header-offset, 0px));
|
||||
height: calc(
|
||||
var(--composer-vh, var(--1dvh)) * 100 - var(--header-offset, 0px)
|
||||
);
|
||||
|
||||
.footer-nav-ipad & {
|
||||
top: calc(var(--header-offset) + var(--footer-nav-height));
|
||||
height: calc(
|
||||
var(--100dvh) - var(--header-offset, 0px) - var(--footer-nav-height, 0px)
|
||||
var(--composer-vh, var(--1dvh)) * 100 - var(--header-offset, 0px) -
|
||||
var(--footer-nav-height, 0px)
|
||||
);
|
||||
}
|
||||
|
||||
|
@ -1,10 +1,8 @@
|
||||
{{#if
|
||||
(and this.showMobileDirectMessageButton this.canCreateDirectMessageChannel)
|
||||
}}
|
||||
{{#if this.showMobileDirectMessageButton}}
|
||||
<LinkTo
|
||||
@route="chat.draft-channel"
|
||||
class="btn-flat open-draft-channel-page-btn keep-mobile-sidebar-open btn-floating"
|
||||
title={{i18n this.createDirectMessageChannelLabel}}
|
||||
title={{i18n "chat.direct_messages.new"}}
|
||||
>
|
||||
{{d-icon "plus"}}
|
||||
</LinkTo>
|
||||
@ -62,6 +60,7 @@
|
||||
/>
|
||||
{{/each}}
|
||||
{{/if}}
|
||||
|
||||
</div>
|
||||
{{/if}}
|
||||
|
||||
|
@ -26,7 +26,7 @@ export default class ChannelsList extends Component {
|
||||
}
|
||||
|
||||
get showMobileDirectMessageButton() {
|
||||
return this.site.mobileView && this.showDirectMessageChannels;
|
||||
return this.site.mobileView && this.canCreateDirectMessageChannel;
|
||||
}
|
||||
|
||||
get inSidebar() {
|
||||
|
@ -1,12 +1,3 @@
|
||||
{{#if this.chatProgressBarContainer}}
|
||||
{{#in-element this.chatProgressBarContainer}}
|
||||
<DProgressBar
|
||||
@key="browse-list"
|
||||
@isLoading={{this.channelsCollection.loading}}
|
||||
/>
|
||||
{{/in-element}}
|
||||
{{/if}}
|
||||
|
||||
<div class="chat-browse-view__header chat-full-page-header">
|
||||
{{#if this.site.mobileView}}
|
||||
<LinkTo
|
||||
@ -75,18 +66,23 @@
|
||||
</div>
|
||||
</div>
|
||||
{{else if this.channelsCollection.length}}
|
||||
<div class="chat-browse-view__content_wrapper">
|
||||
<div class="chat-browse-view__content">
|
||||
<div class="chat-browse-view__cards">
|
||||
{{#each this.channelsCollection as |channel|}}
|
||||
<ChatChannelCard @channel={{channel}} />
|
||||
{{/each}}
|
||||
<LoadMore
|
||||
@selector=".chat-channel-card"
|
||||
@action={{this.channelsCollection.loadMore}}
|
||||
>
|
||||
<div class="chat-browse-view__content_wrapper">
|
||||
<div class="chat-browse-view__content">
|
||||
<div class="chat-browse-view__cards">
|
||||
{{#each this.channelsCollection as |channel|}}
|
||||
<ChatChannelCard @channel={{channel}} />
|
||||
{{/each}}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{{#unless this.channelsCollection.loading}}
|
||||
<OnVisibilityAction @action={{action "onScroll"}} />
|
||||
{{/unless}}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<ConditionalLoadingSpinner
|
||||
@condition={{this.channelsCollection.loading}}
|
||||
/>
|
||||
</LoadMore>
|
||||
{{/if}}
|
||||
</div>
|
@ -1,45 +1,41 @@
|
||||
{{#if this.chatProgressBarContainer}}
|
||||
{{#in-element this.chatProgressBarContainer}}
|
||||
<DProgressBar @key="members-view" @isLoading={{this.members.loading}} />
|
||||
{{/in-element}}
|
||||
{{/if}}
|
||||
|
||||
{{#if (gt this.channel.membershipsCount 0)}}
|
||||
<div class="channel-members-view-wrapper">
|
||||
<div
|
||||
class={{concat
|
||||
"channel-members-view__search-input-container"
|
||||
(if this.isSearchFocused " is-focused")
|
||||
}}
|
||||
>
|
||||
<Input
|
||||
class={{this.inputSelector}}
|
||||
placeholder={{i18n "chat.members_view.filter_placeholder"}}
|
||||
{{on "input" (action "onFilterMembers" value="target.value")}}
|
||||
{{on "focusin" (action (mut this.isSearchFocused) true)}}
|
||||
{{on "focusout" (action (mut this.isSearchFocused) false)}}
|
||||
/>
|
||||
{{d-icon "search"}}
|
||||
</div>
|
||||
<LoadMore
|
||||
@selector=".channel-members-view__list-item"
|
||||
@action={{this.loadMore}}
|
||||
>
|
||||
<div class="channel-members-view-wrapper">
|
||||
<div
|
||||
class={{concat
|
||||
"channel-members-view__search-input-container"
|
||||
(if this.isSearchFocused " is-focused")
|
||||
}}
|
||||
>
|
||||
<Input
|
||||
class={{this.inputSelector}}
|
||||
placeholder={{i18n "chat.members_view.filter_placeholder"}}
|
||||
{{on "input" (action "onFilterMembers" value="target.value")}}
|
||||
{{on "focusin" (action (mut this.isSearchFocused) true)}}
|
||||
{{on "focusout" (action (mut this.isSearchFocused) false)}}
|
||||
/>
|
||||
{{d-icon "search"}}
|
||||
</div>
|
||||
|
||||
<div
|
||||
class="channel-members-view__list-container"
|
||||
{{on "scroll" (action "loadMore")}}
|
||||
>
|
||||
|
||||
<div role="list" class="channel-members-view__list">
|
||||
{{#each this.members as |membership|}}
|
||||
<div class="channel-members-view__list-item">
|
||||
<ChatUserInfo @user={{membership.user}} />
|
||||
</div>
|
||||
{{else}}
|
||||
{{#unless this.isFetchingMembers}}
|
||||
{{i18n "chat.channel.no_memberships_found"}}
|
||||
{{/unless}}
|
||||
{{/each}}
|
||||
<div class="channel-members-view__list-container">
|
||||
<div role="list" class="channel-members-view__list">
|
||||
{{#each this.members as |membership|}}
|
||||
<div class="channel-members-view__list-item">
|
||||
<ChatUserInfo @user={{membership.user}} />
|
||||
</div>
|
||||
{{else}}
|
||||
{{#unless this.isFetchingMembers}}
|
||||
{{i18n "chat.channel.no_memberships_found"}}
|
||||
{{/unless}}
|
||||
{{/each}}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<ConditionalLoadingSpinner @condition={{this.members.loading}} />
|
||||
</LoadMore>
|
||||
{{else}}
|
||||
<div class="channel-members-view-wrapper">
|
||||
{{i18n "chat.channel.no_memberships"}}
|
||||
|
@ -1,6 +1,10 @@
|
||||
<div class="chat-draft">
|
||||
{{#if this.site.mobileView}}
|
||||
<header class="chat-draft-header">
|
||||
<header
|
||||
class="chat-draft-header"
|
||||
{{did-insert this.setChatDraftHeaderHeight}}
|
||||
{{will-destroy this.unsetChatDraftHeaderHeight}}
|
||||
>
|
||||
<FlatButton
|
||||
@class="chat-draft-header__btn btn"
|
||||
@icon="chevron-left"
|
||||
|
@ -14,6 +14,22 @@ export default class ChatDraftChannelScreen extends Component {
|
||||
return this.router.transitionTo("chat.index");
|
||||
}
|
||||
|
||||
@action
|
||||
setChatDraftHeaderHeight(element) {
|
||||
document.documentElement.style.setProperty(
|
||||
"--chat-draft-header-height",
|
||||
`${element.clientHeight}px`
|
||||
);
|
||||
}
|
||||
|
||||
@action
|
||||
unsetChatDraftHeaderHeight() {
|
||||
document.documentElement.style.setProperty(
|
||||
"--chat-draft-header-height",
|
||||
"0px"
|
||||
);
|
||||
}
|
||||
|
||||
@action
|
||||
onChangeSelectedUsers(users) {
|
||||
this._fetchPreviewedChannel(users);
|
||||
|
@ -5,7 +5,11 @@
|
||||
{{/if}}
|
||||
|
||||
{{#if (and this.channel.isDraft (not this.isLoading))}}
|
||||
<div class="direct-message-creator">
|
||||
<div
|
||||
class="direct-message-creator"
|
||||
{{did-insert this.setDirectMessageCreatorHeight}}
|
||||
{{will-destroy this.unsetDirectMessageCreatorHeight}}
|
||||
>
|
||||
<div
|
||||
class="filter-area {{if this.isFilterFocused 'is-focused'}}"
|
||||
role="button"
|
||||
|
@ -126,6 +126,22 @@ export default Component.extend({
|
||||
});
|
||||
},
|
||||
|
||||
@action
|
||||
setDirectMessageCreatorHeight(element) {
|
||||
document.documentElement.style.setProperty(
|
||||
"--chat-direct-message-creator-height",
|
||||
`${element.clientHeight}px`
|
||||
);
|
||||
},
|
||||
|
||||
@action
|
||||
unsetDirectMessageCreatorHeight() {
|
||||
document.documentElement.style.setProperty(
|
||||
"--chat-direct-message-creator-height",
|
||||
"0px"
|
||||
);
|
||||
},
|
||||
|
||||
@action
|
||||
onFilterInput(term) {
|
||||
this.set("term", term);
|
||||
|
@ -428,8 +428,7 @@ body.has-full-page-chat {
|
||||
}
|
||||
}
|
||||
|
||||
.chat-messages-scroll,
|
||||
.chat-channel {
|
||||
.chat-messages-scroll {
|
||||
box-sizing: border-box;
|
||||
height: 100%;
|
||||
}
|
||||
@ -574,30 +573,13 @@ html.has-full-page-chat {
|
||||
height: 100%;
|
||||
width: 100%;
|
||||
|
||||
&.keyboard-visible body #main-outlet .full-page-chat {
|
||||
padding-bottom: 0.2rem;
|
||||
}
|
||||
|
||||
body {
|
||||
height: 100%;
|
||||
width: 100%;
|
||||
|
||||
&.footer-nav-ipad {
|
||||
#main-outlet-wrapper {
|
||||
grid-template-rows: calc(
|
||||
var(--chat-vh, 1vh) * 100 - var(--header-offset, 0px) -
|
||||
var(--footer-nav-height, 0px)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
#main-outlet {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
max-height: calc(
|
||||
var(--chat-vh, 1vh) * 100 - var(--header-offset, 0px) -
|
||||
var(--composer-height, 0px)
|
||||
);
|
||||
|
||||
.full-page-chat {
|
||||
height: 100%;
|
||||
@ -620,32 +602,12 @@ html.has-full-page-chat {
|
||||
|
||||
// these need to apply to desktop too, because iPads
|
||||
&.discourse-touch {
|
||||
// iPad web
|
||||
#main-outlet-wrapper {
|
||||
// restrict the row height, including when virtual keyboard is open
|
||||
grid-template-rows: calc(
|
||||
var(--chat-vh, 1vh) * 100 - var(--header-offset, 0px)
|
||||
);
|
||||
|
||||
.sidebar-wrapper {
|
||||
// prevents sidebar from overflowing behind the virtual keyboard
|
||||
height: 100%;
|
||||
}
|
||||
}
|
||||
|
||||
.full-page-chat,
|
||||
.chat-channel,
|
||||
#main-outlet {
|
||||
// allows containers to shrink to fit
|
||||
min-height: 0;
|
||||
}
|
||||
|
||||
#main-outlet {
|
||||
// limits height for iPad
|
||||
max-height: calc(
|
||||
100vh - calc(var(--header-offset) + var(--composer-ipad-padding))
|
||||
);
|
||||
}
|
||||
}
|
||||
[data-popper-reference-hidden] {
|
||||
visibility: hidden;
|
||||
|
@ -1,16 +1,7 @@
|
||||
.chat-browse-view {
|
||||
position: relative;
|
||||
height: calc(100vh - var(--header-offset) - var(--chat-header-offset));
|
||||
padding-top: 1em;
|
||||
padding-bottom: 41px;
|
||||
box-sizing: border-box;
|
||||
overflow-y: scroll;
|
||||
|
||||
@include chat-scrollbar();
|
||||
|
||||
@include breakpoint(mobile-large) {
|
||||
padding-right: 1rem; //fix for different scroll behaviour on mobile where overflow-y:scroll acts like auto
|
||||
}
|
||||
padding: 1rem;
|
||||
|
||||
&__header {
|
||||
display: flex;
|
||||
@ -28,18 +19,14 @@
|
||||
}
|
||||
|
||||
&__content_wrapper {
|
||||
margin: 2rem 0 0 1rem;
|
||||
box-sizing: border-box;
|
||||
|
||||
@include breakpoint(tablet) {
|
||||
margin-top: 1rem;
|
||||
}
|
||||
margin-top: 1rem;
|
||||
}
|
||||
|
||||
&__cards {
|
||||
display: grid;
|
||||
grid-template-columns: repeat(2, 1fr);
|
||||
grid-gap: 2.5rem;
|
||||
grid-gap: 2rem;
|
||||
|
||||
@include breakpoint(tablet) {
|
||||
grid-template-columns: repeat(1, 1fr);
|
||||
@ -51,7 +38,6 @@
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: end;
|
||||
margin: 0 0 0 1rem;
|
||||
|
||||
@include breakpoint(tablet) {
|
||||
flex-direction: column;
|
||||
|
@ -101,10 +101,6 @@ input.channel-members-view__search-input {
|
||||
flex-direction: column;
|
||||
margin-top: 1em;
|
||||
box-sizing: border-box;
|
||||
min-height: 1px;
|
||||
overflow-y: auto;
|
||||
height: 100%;
|
||||
@include chat-scrollbar();
|
||||
}
|
||||
|
||||
.channel-members-view__list-item {
|
||||
|
@ -7,6 +7,19 @@
|
||||
grid-area: main;
|
||||
width: 100%;
|
||||
min-width: 250px;
|
||||
height: calc(
|
||||
var(--chat-vh, 1vh) * 100 - var(--header-offset, 0px) -
|
||||
var(--composer-height, 0px) - var(--chat-draft-header-height, 0px) -
|
||||
var(--chat-direct-message-creator-height, 0px)
|
||||
);
|
||||
|
||||
.footer-nav-ipad & {
|
||||
height: calc(
|
||||
var(--chat-vh, 1vh) * 100 - var(--header-offset, 0px) -
|
||||
var(--footer-nav-height, 0px) - var(--chat-draft-header-height, 0px) -
|
||||
var(--chat-direct-message-creator-height, 0px)
|
||||
);
|
||||
}
|
||||
|
||||
.open-drawer-btn,
|
||||
.open-thread-list-btn {
|
||||
|
@ -251,4 +251,5 @@ a.chat-drawer-header__title {
|
||||
height: 100%;
|
||||
min-height: 1px;
|
||||
padding-bottom: 0.25em;
|
||||
position: relative;
|
||||
}
|
||||
|
@ -1,3 +1,31 @@
|
||||
.btn-floating.open-draft-channel-page-btn {
|
||||
position: fixed;
|
||||
background: var(--tertiary);
|
||||
bottom: 2rem;
|
||||
right: 2rem;
|
||||
border-radius: 50%;
|
||||
font-size: var(--font-up-4);
|
||||
padding: 1rem;
|
||||
transition: transform 0.25s ease, box-shadow 0.25s ease;
|
||||
z-index: z("usercard");
|
||||
box-shadow: 0px 5px 5px -1px rgba(0, 0, 0, 0.25);
|
||||
|
||||
.d-icon {
|
||||
color: var(--primary-very-low);
|
||||
}
|
||||
|
||||
&:active {
|
||||
box-shadow: 0px 0px 5px -1px rgba(0, 0, 0, 0.25);
|
||||
transform: scale(0.9);
|
||||
}
|
||||
|
||||
&:focus {
|
||||
@include default-focus;
|
||||
border-color: var(--quaternary);
|
||||
outline-color: var(--quaternary);
|
||||
}
|
||||
}
|
||||
|
||||
.channels-list {
|
||||
overflow-y: auto;
|
||||
overscroll-behavior: contain;
|
||||
|
@ -76,32 +76,4 @@
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.btn-floating.open-draft-channel-page-btn {
|
||||
position: absolute;
|
||||
background: var(--tertiary);
|
||||
bottom: 2.5rem;
|
||||
right: 2.5rem;
|
||||
border-radius: 50%;
|
||||
font-size: var(--font-up-4);
|
||||
padding: 1rem;
|
||||
transition: transform 0.25s ease, box-shadow 0.25s ease;
|
||||
z-index: z("usercard");
|
||||
box-shadow: 0px 5px 5px -1px rgba(0, 0, 0, 0.25);
|
||||
|
||||
.d-icon {
|
||||
color: var(--primary-very-low);
|
||||
}
|
||||
|
||||
&:active {
|
||||
box-shadow: 0px 0px 5px -1px rgba(0, 0, 0, 0.25);
|
||||
transform: scale(0.9);
|
||||
}
|
||||
|
||||
&:focus {
|
||||
@include default-focus;
|
||||
border-color: var(--quaternary);
|
||||
outline-color: var(--quaternary);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user