
import { registerCss } from '../../../../../../../css.js';
import { __decorate, __param } from '../../../../../../../external/tslib/tslib.es6.js';
import * as notificationsCenter from './media/notificationsCenter.css';
import * as notificationsActions from './media/notificationsActions.css';
import { NOTIFICATIONS_CENTER_BORDER, NOTIFICATIONS_CENTER_HEADER_FOREGROUND, NOTIFICATIONS_CENTER_HEADER_BACKGROUND } from '../../../common/theme.js';
import { Themable } from '../../../../platform/theme/common/themeService.js';
import { IThemeService } from '../../../../platform/theme/common/themeService.service.js';
import { NotificationsSettings, getNotificationsPosition, NotificationsPosition, NotificationChangeType, NotificationViewItemContentChangeKind } from '../../../common/notifications.js';
import { Parts } from '../../../services/layout/browser/layoutService.js';
import { IWorkbenchLayoutService } from '../../../services/layout/browser/layoutService.service.js';
import { Emitter } from '../../../../base/common/event.js';
import { IContextKeyService } from '../../../../platform/contextkey/common/contextkey.service.js';
import { NotificationActionRunner } from './notificationsCommands.js';
import { NotificationsList } from './notificationsList.js';
import { IInstantiationService } from '../../../../platform/instantiation/common/instantiation.js';
import { Dimension, $, isAncestorOfActiveElement } from '../../../../base/browser/dom.js';
import { IEditorGroupsService } from '../../../services/editor/common/editorGroupsService.service.js';
import { localize } from '../../../../nls.js';
import { ActionBar } from '../../../../base/browser/ui/actionbar/actionbar.js';
import { hideUpIcon, hideIcon, ConfigureNotificationsPositionAction, ConfigureDoNotDisturbAction, ToggleDoNotDisturbAction, ToggleDoNotDisturbBySourceAction, ClearAllNotificationsAction, HideNotificationsCenterAction } from './notificationsActions.js';
import { Separator, toAction } from '../../../../base/common/actions.js';
import { MenuId } from '../../../../platform/actions/common/actions.js';
import { IMenuService } from '../../../../platform/actions/common/actions.service.js';
import { createActionViewItem } from '../../../../platform/actions/browser/menuEntryActionViewItem.js';
import { IKeybindingService } from '../../../../platform/keybinding/common/keybinding.service.js';
import { assertReturnsDefined, assertReturnsAllDefined } from '../../../../base/common/types.js';
import { NotificationsCenterVisibleContext } from '../../../common/contextkeys.js';
import { NotificationsFilter } from '../../../../platform/notification/common/notification.js';
import { INotificationService } from '../../../../platform/notification/common/notification.service.js';
import { mainWindow } from '../../../../base/browser/window.js';
import { IContextMenuService } from '../../../../platform/contextview/browser/contextView.service.js';
import { DropdownMenuActionViewItem } from '../../../../base/browser/ui/dropdown/dropdownActionViewItem.js';
import { AccessibilitySignal } from '../../../../platform/accessibilitySignal/browser/accessibilitySignalService.js';
import { IAccessibilitySignalService } from '../../../../platform/accessibilitySignal/browser/accessibilitySignalService.service.js';
import { IConfigurationService } from '../../../../platform/configuration/common/configuration.service.js';
import { DEFAULT_CUSTOM_TITLEBAR_HEIGHT } from '../../../../platform/window/common/window.js';
import { ThemeIcon } from '../../../../base/common/themables.js';

var NotificationsCenter_1;
registerCss(notificationsCenter);
registerCss(notificationsActions);
let NotificationsCenter = class NotificationsCenter extends Themable {
    static {
        NotificationsCenter_1 = this;
    }
    static {
        this.MAX_DIMENSIONS = ( new Dimension(450, 400));
    }
    static {
        this.MAX_NOTIFICATION_SOURCES = 10;
    }
    constructor(
        container,
        model,
        themeService,
        instantiationService,
        layoutService,
        contextKeyService,
        editorGroupService,
        keybindingService,
        notificationService,
        accessibilitySignalService,
        contextMenuService,
        configurationService,
        menuService
    ) {
        super(themeService);
        this.container = container;
        this.model = model;
        this.instantiationService = instantiationService;
        this.layoutService = layoutService;
        this.contextKeyService = contextKeyService;
        this.editorGroupService = editorGroupService;
        this.keybindingService = keybindingService;
        this.notificationService = notificationService;
        this.accessibilitySignalService = accessibilitySignalService;
        this.contextMenuService = contextMenuService;
        this.configurationService = configurationService;
        this.menuService = menuService;
        this._onDidChangeVisibility = this._register(( new Emitter()));
        this.onDidChangeVisibility = this._onDidChangeVisibility.event;
        this.notificationsCenterVisibleContextKey = NotificationsCenterVisibleContext.bindTo(contextKeyService);
        this.registerListeners();
    }
    registerListeners() {
        this._register(this.model.onDidChangeNotification(e => this.onDidChangeNotification(e)));
        this._register(
            this.layoutService.onDidLayoutMainContainer(dimension => this.layout(Dimension.lift(dimension)))
        );
        this._register(this.notificationService.onDidChangeFilter(() => this.onDidChangeFilter()));
        this._register(this.configurationService.onDidChangeConfiguration(e => {
            if (e.affectsConfiguration(NotificationsSettings.NOTIFICATIONS_POSITION)) {
                this.updatePositionClass();
            }
        }));
    }
    updatePositionClass() {
        if (!this.notificationsCenterContainer) {
            return;
        }
        const position = getNotificationsPosition(this.configurationService);
        this.notificationsCenterContainer.classList.remove("bottom-right", "bottom-left", "top-right");
        this.notificationsCenterContainer.classList.add(position);
        this.updateHideActionIcon();
        this.updateTopOffset();
    }
    updateHideActionIcon() {
        if (!this.hideAction) {
            return;
        }
        const position = getNotificationsPosition(this.configurationService);
        this.hideAction.class = ThemeIcon.asClassName(position === NotificationsPosition.TOP_RIGHT ? hideUpIcon : hideIcon);
    }
    updateTopOffset() {
        if (!this.notificationsCenterContainer) {
            return;
        }
        const position = getNotificationsPosition(this.configurationService);
        if (position === NotificationsPosition.TOP_RIGHT) {
            let topOffset = 7;
            if (this.layoutService.isVisible(Parts.TITLEBAR_PART, mainWindow)) {
                topOffset += DEFAULT_CUSTOM_TITLEBAR_HEIGHT;
            }
            this.notificationsCenterContainer.style.top = `${topOffset}px`;
        } else {
            this.notificationsCenterContainer.style.top = "";
        }
    }
    onDidChangeFilter() {
        if (this.notificationService.getFilter() === NotificationsFilter.ERROR) {
            this.hide();
        }
    }
    get isVisible() {
        return !!this._isVisible;
    }
    show() {
        if (this._isVisible) {
            const notificationsList = assertReturnsDefined(this.notificationsList);
            notificationsList.show();
            notificationsList.focusFirst();
            return;
        }
        if (!this.notificationsCenterContainer) {
            this.create();
        }
        this.updateTitle();
        const [notificationsList, notificationsCenterContainer] = assertReturnsAllDefined(this.notificationsList, this.notificationsCenterContainer);
        this._isVisible = true;
        notificationsCenterContainer.classList.add("visible");
        notificationsList.show();
        this.layout(this.workbenchDimensions);
        notificationsList.updateNotificationsList(0, 0, this.model.notifications);
        notificationsList.focusFirst();
        this.updateStyles();
        this.model.notifications.forEach(notification => notification.updateVisibility(true));
        this.notificationsCenterVisibleContextKey.set(true);
        this._onDidChangeVisibility.fire();
    }
    updateTitle() {
        const [notificationsCenterTitle, clearAllAction] = assertReturnsAllDefined(this.notificationsCenterTitle, this.clearAllAction);
        if (this.model.notifications.length === 0) {
            notificationsCenterTitle.textContent = ( localize(3747, "No new notifications"));
            clearAllAction.enabled = false;
        } else {
            notificationsCenterTitle.textContent = ( localize(3748, "Notifications"));
            clearAllAction.enabled = ( this.model.notifications.some(notification => !notification.hasProgress));
        }
    }
    create() {
        this.notificationsCenterContainer = $(".notifications-center");
        this.updatePositionClass();
        this.notificationsCenterHeader = $(".notifications-center-header");
        this.notificationsCenterContainer.appendChild(this.notificationsCenterHeader);
        this.notificationsCenterTitle = $("span.notifications-center-header-title");
        this.notificationsCenterHeader.appendChild(this.notificationsCenterTitle);
        const toolbarContainer = $(".notifications-center-header-toolbar");
        this.notificationsCenterHeader.appendChild(toolbarContainer);
        const actionRunner = this._register(this.instantiationService.createInstance(NotificationActionRunner));
        const that = this;
        const notificationsToolBar = this._register(( new ActionBar(toolbarContainer, {
            ariaLabel: ( localize(3749, "Notification Center Actions")),
            actionRunner,
            actionViewItemProvider: (action, options) => {
                if (action.id === ConfigureNotificationsPositionAction.ID) {
                    return this._register(
                        this.instantiationService.createInstance(DropdownMenuActionViewItem, action, {
                            getActions: () => Separator.join(...( this.menuService.getMenuActions(MenuId.NotificationsCenterPositionMenu, this.contextKeyService).map(([, actions]) => actions)))
                        }, this.contextMenuService, {
                            ...options,
                            actionRunner,
                            classNames: action.class,
                            keybindingProvider: action => this.keybindingService.lookupKeybinding(action.id)
                        })
                    );
                }
                if (action.id === ConfigureDoNotDisturbAction.ID) {
                    return this._register(
                        this.instantiationService.createInstance(DropdownMenuActionViewItem, action, {
                            getActions() {
                                const actions = [toAction({
                                    id: ToggleDoNotDisturbAction.ID,
                                    label: that.notificationService.getFilter() === NotificationsFilter.OFF ? ( localize(3750, "Enable Do Not Disturb Mode")) : ( localize(3751, "Disable Do Not Disturb Mode")),
                                    run: () => that.notificationService.setFilter(
                                        that.notificationService.getFilter() === NotificationsFilter.OFF ? NotificationsFilter.ERROR : NotificationsFilter.OFF
                                    )
                                })];
                                const sortedFilters = that.notificationService.getFilters().sort((a, b) => a.label.localeCompare(b.label));
                                for (const source of sortedFilters.slice(0, NotificationsCenter_1.MAX_NOTIFICATION_SOURCES)) {
                                    if (actions.length === 1) {
                                        actions.push(( new Separator()));
                                    }
                                    actions.push(toAction({
                                        id: `${ToggleDoNotDisturbAction.ID}.${source.id}`,
                                        label: source.label,
                                        checked: source.filter !== NotificationsFilter.ERROR,
                                        run: () => that.notificationService.setFilter({
                                            ...source,
                                            filter: source.filter === NotificationsFilter.ERROR ? NotificationsFilter.OFF : NotificationsFilter.ERROR
                                        })
                                    }));
                                }
                                if (sortedFilters.length > NotificationsCenter_1.MAX_NOTIFICATION_SOURCES) {
                                    actions.push(( new Separator()));
                                    actions.push(that._register(that.instantiationService.createInstance(
                                        ToggleDoNotDisturbBySourceAction,
                                        ToggleDoNotDisturbBySourceAction.ID,
                                        ( localize(3752, "More…"))
                                    )));
                                }
                                return actions;
                            }
                        }, this.contextMenuService, {
                            ...options,
                            actionRunner,
                            classNames: action.class,
                            keybindingProvider: action => this.keybindingService.lookupKeybinding(action.id)
                        })
                    );
                }
                return createActionViewItem(this.instantiationService, action, options);
            }
        })));
        this.clearAllAction = this._register(this.instantiationService.createInstance(
            ClearAllNotificationsAction,
            ClearAllNotificationsAction.ID,
            ClearAllNotificationsAction.LABEL
        ));
        notificationsToolBar.push(this.clearAllAction, {
            icon: true,
            label: false,
            keybinding: this.getKeybindingLabel(this.clearAllAction)
        });
        this.configureDoNotDisturbAction = this._register(this.instantiationService.createInstance(
            ConfigureDoNotDisturbAction,
            ConfigureDoNotDisturbAction.ID,
            ConfigureDoNotDisturbAction.LABEL
        ));
        notificationsToolBar.push(this.configureDoNotDisturbAction, {
            icon: true,
            label: false
        });
        const configureNotificationsPositionAction = this._register(this.instantiationService.createInstance(
            ConfigureNotificationsPositionAction,
            ConfigureNotificationsPositionAction.ID,
            ConfigureNotificationsPositionAction.LABEL
        ));
        notificationsToolBar.push(configureNotificationsPositionAction, {
            icon: true,
            label: false
        });
        this.hideAction = this._register(this.instantiationService.createInstance(
            HideNotificationsCenterAction,
            HideNotificationsCenterAction.ID,
            HideNotificationsCenterAction.LABEL
        ));
        this.updateHideActionIcon();
        notificationsToolBar.push(this.hideAction, {
            icon: true,
            label: false,
            keybinding: this.getKeybindingLabel(this.hideAction)
        });
        this.notificationsList = this.instantiationService.createInstance(NotificationsList, this.notificationsCenterContainer, {
            widgetAriaLabel: ( localize(3753, "Notifications Center"))
        });
        this.container.appendChild(this.notificationsCenterContainer);
    }
    getKeybindingLabel(action) {
        const keybinding = this.keybindingService.lookupKeybinding(action.id);
        return keybinding ? keybinding.getLabel() : null;
    }
    onDidChangeNotification(e) {
        if (!this._isVisible) {
            return;
        }
        let focusEditor = false;
        const [notificationsList, notificationsCenterContainer] = assertReturnsAllDefined(this.notificationsList, this.notificationsCenterContainer);
        switch (e.kind) {
        case NotificationChangeType.ADD:
            notificationsList.updateNotificationsList(e.index, 0, [e.item]);
            e.item.updateVisibility(true);
            break;
        case NotificationChangeType.CHANGE:
            switch (e.detail) {
            case NotificationViewItemContentChangeKind.ACTIONS:
                notificationsList.updateNotificationsList(e.index, 1, [e.item]);
                break;
            case NotificationViewItemContentChangeKind.MESSAGE:
                if (e.item.expanded) {
                    notificationsList.updateNotificationHeight(e.item);
                }
                break;
            }
            break;
        case NotificationChangeType.EXPAND_COLLAPSE:
            notificationsList.updateNotificationsList(e.index, 1, [e.item]);
            break;
        case NotificationChangeType.REMOVE:
            focusEditor = isAncestorOfActiveElement(notificationsCenterContainer);
            notificationsList.updateNotificationsList(e.index, 1);
            e.item.updateVisibility(false);
            break;
        }
        this.updateTitle();
        if (this.model.notifications.length === 0) {
            this.hide();
            if (focusEditor) {
                this.editorGroupService.activeGroup.focus();
            }
        }
    }
    hide() {
        if (!this._isVisible || !this.notificationsCenterContainer || !this.notificationsList) {
            return;
        }
        const focusEditor = isAncestorOfActiveElement(this.notificationsCenterContainer);
        this._isVisible = false;
        this.notificationsCenterContainer.classList.remove("visible");
        this.notificationsList.hide();
        this.model.notifications.forEach(notification => notification.updateVisibility(false));
        this.notificationsCenterVisibleContextKey.set(false);
        this._onDidChangeVisibility.fire();
        if (focusEditor) {
            this.editorGroupService.activeGroup.focus();
        }
    }
    updateStyles() {
        if (this.notificationsCenterContainer && this.notificationsCenterHeader) {
            const borderColor = this.getColor(NOTIFICATIONS_CENTER_BORDER);
            this.notificationsCenterContainer.style.border = borderColor ? `1px solid ${borderColor}` : "";
            const headerForeground = this.getColor(NOTIFICATIONS_CENTER_HEADER_FOREGROUND);
            this.notificationsCenterHeader.style.color = headerForeground ?? "";
            const headerBackground = this.getColor(NOTIFICATIONS_CENTER_HEADER_BACKGROUND);
            this.notificationsCenterHeader.style.background = headerBackground ?? "";
        }
    }
    layout(dimension) {
        this.workbenchDimensions = dimension;
        if (this._isVisible && this.notificationsCenterContainer) {
            const maxWidth = NotificationsCenter_1.MAX_DIMENSIONS.width;
            const maxHeight = NotificationsCenter_1.MAX_DIMENSIONS.height;
            let availableWidth = maxWidth;
            let availableHeight = maxHeight;
            if (this.workbenchDimensions) {
                availableWidth = this.workbenchDimensions.width;
                availableWidth -= (2 * 8);
                availableHeight = this.workbenchDimensions.height - 35 ;
                if (this.layoutService.isVisible(Parts.STATUSBAR_PART, mainWindow)) {
                    availableHeight -= 22;
                }
                if (this.layoutService.isVisible(Parts.TITLEBAR_PART, mainWindow)) {
                    availableHeight -= 22;
                }
                availableHeight -= (2 * 12);
            }
            this.updateTopOffset();
            const notificationsList = assertReturnsDefined(this.notificationsList);
            notificationsList.layout(Math.min(maxWidth, availableWidth), Math.min(maxHeight, availableHeight));
        }
    }
    clearAll() {
        this.hide();
        for (const notification of [...this.model.notifications] ) {
            if (!notification.hasProgress) {
                notification.close();
            }
            this.accessibilitySignalService.playSignal(AccessibilitySignal.clear);
        }
    }
};
NotificationsCenter = NotificationsCenter_1 = ( __decorate([( __param(2, IThemeService)), ( __param(3, IInstantiationService)), ( __param(4, IWorkbenchLayoutService)), ( __param(5, IContextKeyService)), ( __param(6, IEditorGroupsService)), ( __param(7, IKeybindingService)), ( __param(8, INotificationService)), ( __param(9, IAccessibilitySignalService)), ( __param(10, IContextMenuService)), ( __param(11, IConfigurationService)), ( __param(12, IMenuService))], NotificationsCenter));

export { NotificationsCenter };
