diff --git a/public/app/containers/Teams/TeamList.tsx b/public/app/containers/Teams/TeamList.tsx index 4429764b1cc..b86763d8799 100644 --- a/public/app/containers/Teams/TeamList.tsx +++ b/public/app/containers/Teams/TeamList.tsx @@ -5,7 +5,7 @@ import PageHeader from 'app/core/components/PageHeader/PageHeader'; import { NavStore } from 'app/stores/NavStore/NavStore'; import { TeamsStore, ITeam } from 'app/stores/TeamsStore/TeamsStore'; import { BackendSrv } from 'app/core/services/backend_srv'; -import appEvents from 'app/core/app_events'; +import DeleteButton from 'app/core/components/DeleteButton/DeleteButton'; interface Props { nav: typeof NavStore.Type; @@ -28,18 +28,6 @@ export class TeamList extends React.Component { } deleteTeam(team: ITeam) { - appEvents.emit('confirm-modal', { - title: 'Delete', - text: 'Are you sure you want to delete Team ' + team.name + '?', - yesText: 'Delete', - icon: 'fa-warning', - onConfirm: () => { - this.deleteTeamConfirmed(team); - }, - }); - } - - deleteTeamConfirmed(team) { this.props.backendSrv.delete('/api/teams/' + team.id).then(this.fetchTeams.bind(this)); } @@ -67,9 +55,7 @@ export class TeamList extends React.Component { {team.memberCount} - this.deleteTeam(team)} className="btn btn-danger btn-small"> - - + this.deleteTeam(team)} /> ); @@ -102,7 +88,7 @@ export class TeamList extends React.Component { -
+
diff --git a/public/app/core/components/DeleteButton/DeleteButton.jest.tsx b/public/app/core/components/DeleteButton/DeleteButton.jest.tsx new file mode 100644 index 00000000000..12acadee18a --- /dev/null +++ b/public/app/core/components/DeleteButton/DeleteButton.jest.tsx @@ -0,0 +1,44 @@ +import React from 'react'; +import DeleteButton from './DeleteButton'; +import { shallow } from 'enzyme'; + +describe('DeleteButton', () => { + let wrapper; + let deleted; + + beforeAll(() => { + deleted = false; + + function deleteItem() { + deleted = true; + } + wrapper = shallow( deleteItem()} />); + }); + + it('should show confirm delete when clicked', () => { + expect(wrapper.state().showConfirm).toBe(false); + wrapper.find('.delete-button').simulate('click'); + expect(wrapper.state().showConfirm).toBe(true); + }); + + it('should hide confirm delete when clicked', () => { + wrapper.find('.delete-button').simulate('click'); + expect(wrapper.state().showConfirm).toBe(true); + wrapper + .find('.confirm-delete') + .find('.btn') + .at(0) + .simulate('click'); + expect(wrapper.state().showConfirm).toBe(false); + }); + + it('should show confirm delete when clicked', () => { + expect(deleted).toBe(false); + wrapper + .find('.confirm-delete') + .find('.btn') + .at(1) + .simulate('click'); + expect(deleted).toBe(true); + }); +}); diff --git a/public/app/core/components/DeleteButton/DeleteButton.tsx b/public/app/core/components/DeleteButton/DeleteButton.tsx new file mode 100644 index 00000000000..a83ce6097ad --- /dev/null +++ b/public/app/core/components/DeleteButton/DeleteButton.tsx @@ -0,0 +1,66 @@ +import React, { PureComponent } from 'react'; + +export interface DeleteButtonProps { + onConfirmDelete(); +} + +export interface DeleteButtonStates { + showConfirm: boolean; +} + +export default class DeleteButton extends PureComponent { + state: DeleteButtonStates = { + showConfirm: false, + }; + + onClickDelete = event => { + if (event) { + event.preventDefault(); + } + + this.setState({ + showConfirm: true, + }); + }; + + onClickCancel = event => { + if (event) { + event.preventDefault(); + } + this.setState({ + showConfirm: false, + }); + }; + + render() { + const onClickConfirm = this.props.onConfirmDelete; + let showConfirm; + let showDeleteButton; + + if (this.state.showConfirm) { + showConfirm = 'show'; + showDeleteButton = 'hide'; + } else { + showConfirm = 'hide'; + showDeleteButton = 'show'; + } + + return ( + + + + + + + + Cancel + + + Confirm Delete + + + + + ); + } +} diff --git a/public/sass/_grafana.scss b/public/sass/_grafana.scss index 9e3bec267ed..3a72bd45a1a 100644 --- a/public/sass/_grafana.scss +++ b/public/sass/_grafana.scss @@ -93,6 +93,7 @@ @import 'components/form_select_box'; @import 'components/user-picker'; @import 'components/description-picker'; +@import 'components/delete_button'; // PAGES @import 'pages/login'; diff --git a/public/sass/components/_delete_button.scss b/public/sass/components/_delete_button.scss new file mode 100644 index 00000000000..e56a1181a09 --- /dev/null +++ b/public/sass/components/_delete_button.scss @@ -0,0 +1,50 @@ +// sets a fixed width so that the rest of the table +// isn't affected by the animation +.delete-button-container { + width: 24px; + direction: rtl; + display: flex; + align-items: center; +} + +//this container is used to make sure confirm-delete isn't +//shown outside of table +.confirm-delete-container { + overflow: hidden; + width: 145px; + position: absolute; + z-index: 1; +} + +.delete-button { + position: absolute; + + &.show { + opacity: 1; + transition: opacity 0.1s ease; + z-index: 2; + } + + &.hide { + opacity: 0; + transition: opacity 0.1s ease; + z-index: 0; + } +} + +.confirm-delete { + display: flex; + align-items: flex-start; + + &.show { + opacity: 1; + transition: opacity 0.08s ease-out, transform 0.1s ease-out; + transform: translateX(0); + } + + &.hide { + opacity: 0; + transition: opacity 0.12s ease-in, transform 0.14s ease-in; + transform: translateX(100px); + } +}