-
+
+
diff --git a/src/Umbraco.Web.UI.Login/src/components/external-login-provider.element.ts b/src/Umbraco.Web.UI.Login/src/components/external-login-provider.element.ts
index 6f0570a91b..a577bbbb0d 100644
--- a/src/Umbraco.Web.UI.Login/src/components/external-login-provider.element.ts
+++ b/src/Umbraco.Web.UI.Login/src/components/external-login-provider.element.ts
@@ -6,10 +6,13 @@ import { until } from 'lit/directives/until.js';
import { loadCustomView, renderCustomView } from '../utils/load-custom-view.function.js';
import { umbLocalizationContext } from '../external/localization/localization-context.js';
+type UserViewState = 'loggingIn' | 'loggedIn' | 'loggedOut' | 'timedOut';
+
type ExternalLoginCustomViewElement = HTMLElement & {
- displayName: string;
- providerName: string;
- externalLoginUrl: string;
+ displayName?: string;
+ providerName?: string;
+ externalLoginUrl?: string;
+ userViewState?: UserViewState;
};
/**
@@ -50,6 +53,17 @@ export class UmbExternalLoginProviderElement extends LitElement {
@property({attribute: 'provider-name'})
providerName = '';
+ /**
+ * Gets or sets the view state of the user. This indicates in which state the user is in the login process,
+ * which can be used to determine where the external-login-provider is being shown.
+ *
+ * @attr user-view-state
+ * @example loggingIn
+ * @default loggingIn
+ */
+ @property({attribute: 'user-view-state'})
+ userViewState: UserViewState = 'loggingIn';
+
/**
* Gets or sets the url to the external login provider.
*
@@ -68,7 +82,6 @@ export class UmbExternalLoginProviderElement extends LitElement {
return this.#externalLoginUrl;
}
-
/**
* Gets or sets the icon to display next to the provider name.
* This should be the name of an icon in the Umbraco Backoffice icon set.
@@ -104,6 +117,17 @@ export class UmbExternalLoginProviderElement extends LitElement {
#externalLoginUrl = '';
+ constructor() {
+ super();
+
+ const searchParams = new URLSearchParams(window.location.search);
+ const isLogout = searchParams.get('logout') === 'true';
+
+ if (isLogout) {
+ this.userViewState = 'loggedOut';
+ }
+ }
+
protected render() {
return this.customView
? until(this.renderCustomView(), html`
@@ -146,6 +170,7 @@ export class UmbExternalLoginProviderElement extends LitElement {
customView.displayName = this.displayName;
customView.providerName = this.providerName;
customView.externalLoginUrl = this.externalLoginUrl;
+ customView.userViewState = this.userViewState;
}
return renderCustomView(customView);
diff --git a/src/Umbraco.Web.UI.Login/src/components/pages/login.page.element.ts b/src/Umbraco.Web.UI.Login/src/components/pages/login.page.element.ts
index 460b867896..565ea08a98 100644
--- a/src/Umbraco.Web.UI.Login/src/components/pages/login.page.element.ts
+++ b/src/Umbraco.Web.UI.Login/src/components/pages/login.page.element.ts
@@ -95,10 +95,12 @@ export default class UmbLoginPageElement extends LitElement {
render() {
return html`
-
- Welcome
-
-
+
${this.disableLocalLogin
? nothing
: html`
@@ -158,6 +160,18 @@ export default class UmbLoginPageElement extends LitElement {
flex-direction: column;
}
+ #header {
+ text-align: center;
+ display: flex;
+ flex-direction: column;
+ gap: var(--uui-size-space-5);
+ }
+
+ #header span {
+ color: var(--uui-color-text-alt); /* TODO Change to uui color when uui gets a muted text variable */
+ font-size: 14px;
+ }
+
#greeting {
color: var(--uui-color-interactive);
text-align: center;
diff --git a/src/Umbraco.Web.UI.Login/src/external/custom-view.element.ts b/src/Umbraco.Web.UI.Login/src/external/custom-view.element.ts
index 0bc3ba8719..693b024321 100644
--- a/src/Umbraco.Web.UI.Login/src/external/custom-view.element.ts
+++ b/src/Umbraco.Web.UI.Login/src/external/custom-view.element.ts
@@ -6,30 +6,32 @@ import {loadCustomView, renderCustomView} from "../utils/load-custom-view.functi
@customElement('umb-custom-view')
export default class UmbCustomViewElement extends LitElement {
@property({ attribute: 'custom-view' })
- customView?: string;
+ set customView (value: string) {
+ this.#customView = value;
+ this.#loadView();
+ }
- @property({ attribute: 'args' })
- args?: any;
+ @property({ type: Object, attribute: 'args'})
+ set args (value: any) {
+ this.#args = value;
+ this.#loadView();
+ }
@state()
protected component: any = null;
- attributeChangedCallback(name: string, _old: string | null, value: string | null) {
- super.attributeChangedCallback(name, _old, value);
- if (name === 'custom-view') {
- this.#loadView();
- }
- }
+ #args?: any;
+ #customView?: string;
async #loadView() {
- if (!this.customView || !this.customView.endsWith('.js') && !this.customView.endsWith('.html')) {
+ if (!this.#customView || !this.#customView.endsWith('.js') && !this.#customView.endsWith('.html')) {
return;
}
- const customView = await loadCustomView(this.customView);
+ const customView = await loadCustomView(this.#customView);
- if (this.args) {
- Object.entries(this.args).forEach(([key, value]) => {
+ if (this.#args) {
+ Object.entries(this.#args).forEach(([key, value]) => {
(customView as any)[key] = value;
});
}
diff --git a/src/Umbraco.Web.UI.Login/src/mocks/customViews/my-custom-view.js b/src/Umbraco.Web.UI.Login/src/mocks/customViews/my-custom-view.js
index f60df70033..c53603f126 100644
--- a/src/Umbraco.Web.UI.Login/src/mocks/customViews/my-custom-view.js
+++ b/src/Umbraco.Web.UI.Login/src/mocks/customViews/my-custom-view.js
@@ -8,7 +8,7 @@ template.innerHTML = `
- My Custom button ()
+ My Custom button ( / )
`;
@@ -16,6 +16,7 @@ template.innerHTML = `
export class MyCustomView extends HTMLElement {
providerName = '';
displayName = '';
+ userViewState = '';
constructor() {
super();
this.attachShadow({ mode: 'open' });
@@ -29,6 +30,7 @@ export class MyCustomView extends HTMLElement {
connectedCallback() {
console.log('My custom view connected');
this.shadowRoot.getElementById('providerName').innerText = this.providerName;
+ this.shadowRoot.getElementById('userViewState').innerText = this.userViewState;
}
}