diff --git a/awx/ui_next/src/components/ContentLoading/ContentLoading.jsx b/awx/ui_next/src/components/ContentLoading/ContentLoading.jsx index f242bbca10..90747007da 100644 --- a/awx/ui_next/src/components/ContentLoading/ContentLoading.jsx +++ b/awx/ui_next/src/components/ContentLoading/ContentLoading.jsx @@ -4,8 +4,8 @@ import { withI18n } from '@lingui/react'; import { EmptyState, EmptyStateBody } from '@patternfly/react-core'; // TODO: Better loading state - skeleton lines / spinner, etc. -const ContentLoading = ({ i18n }) => ( - +const ContentLoading = ({ className, i18n }) => ( + {i18n._(t`Loading...`)} ); diff --git a/awx/ui_next/src/components/Lookup/MultiCredentialsLookup.jsx b/awx/ui_next/src/components/Lookup/MultiCredentialsLookup.jsx index 1a020cab26..0a472e361f 100644 --- a/awx/ui_next/src/components/Lookup/MultiCredentialsLookup.jsx +++ b/awx/ui_next/src/components/Lookup/MultiCredentialsLookup.jsx @@ -37,6 +37,7 @@ function MultiCredentialsLookup(props) { const [selectedType, setSelectedType] = useState(null); const [credentials, setCredentials] = useState([]); const [credentialsCount, setCredentialsCount] = useState(0); + const [isLoading, setIsLoading] = useState(false); useEffect(() => { (async () => { @@ -56,6 +57,7 @@ function MultiCredentialsLookup(props) { return; } try { + setIsLoading(true); const params = parseQueryString(QS_CONFIG, history.location.search); const { results, count } = await loadCredentials( params, @@ -63,6 +65,7 @@ function MultiCredentialsLookup(props) { ); setCredentials(results); setCredentialsCount(count); + setIsLoading(false); } catch (err) { onError(err); } @@ -133,6 +136,7 @@ function MultiCredentialsLookup(props) { name="credentials" qsConfig={QS_CONFIG} readOnly={!canDelete} + isLoading={isLoading} selectItem={item => { if (isMultiple) { return dispatch({ type: 'SELECT_ITEM', item }); diff --git a/awx/ui_next/src/components/PaginatedDataList/PaginatedDataList.jsx b/awx/ui_next/src/components/PaginatedDataList/PaginatedDataList.jsx index e89431d3a8..223bcd5950 100644 --- a/awx/ui_next/src/components/PaginatedDataList/PaginatedDataList.jsx +++ b/awx/ui_next/src/components/PaginatedDataList/PaginatedDataList.jsx @@ -25,10 +25,34 @@ import PaginatedDataListItem from './PaginatedDataListItem'; class PaginatedDataList extends React.Component { constructor(props) { super(props); + this.state = { + height: 0, + }; + this.ref = React.createRef(); this.handleSetPage = this.handleSetPage.bind(this); this.handleSetPageSize = this.handleSetPageSize.bind(this); } + componentDidUpdate(prevProps) { + const { items } = this.props; + if (prevProps.items !== items) { + this.findHeight(); + } + } + + findHeight() { + if (!this.ref || !this.ref.current) { + return; + } + const { state } = this; + const height = this.ref.current.scrollHeight; + if (height && height !== state.height) { + this.setState({ + height: this.ref.current.scrollHeight, + }); + } + } + handleSetPage(event, pageNumber) { const { history, qsConfig } = this.props; const { search } = history.location; @@ -66,6 +90,7 @@ class PaginatedDataList extends React.Component { i18n, renderToolbar, } = this.props; + const { height } = this.state; const columns = toolbarColumns.length ? toolbarColumns : [ @@ -85,8 +110,14 @@ class PaginatedDataList extends React.Component { const emptyContentTitle = i18n._(t`No ${pluralizedItemName} Found `); let Content; - if (hasContentLoading && items.length <= 0) { - Content = ; + if (hasContentLoading) { + Content = ( + + ); } else if (contentError) { Content = ; } else if (items.length <= 0) { @@ -100,7 +131,7 @@ class PaginatedDataList extends React.Component { } return ( - +
) : null} - +
); } }