diff --git a/test/spec/controllers/groupCtrlSpec.js b/test/spec/controllers/groupCtrlSpec.js index c214c8ed9f..2f153fc390 100644 --- a/test/spec/controllers/groupCtrlSpec.js +++ b/test/spec/controllers/groupCtrlSpec.js @@ -70,4 +70,139 @@ describe('Groups Controller', function() { expect(myGuilds).to.be.calledOnce; }); }); + + describe('editGroup', () => { + var guild; + + beforeEach(() => { + guild = specHelper.newGroup({ + _id: 'unique-guild-id', + leader: 'old leader', + type: 'guild', + members: ['not-user-id'], + $save: sandbox.spy(), + }); + }); + + it('marks group as being in edit mode', () => { + scope.editGroup(guild); + + expect(guild._editing).to.eql(true); + }); + + it('copies group to groupCopy', () => { + scope.editGroup(guild); + + for (var key in scope.groupCopy) { + expect(scope.groupCopy[key]).to.eql(guild[key]); + } + }); + + it('does not change original group when groupCopy is changed', () => { + scope.editGroup(guild); + + scope.groupCopy.leader = 'new leader'; + expect(scope.groupCopy.leader).to.not.eql(guild.leader); + }); + + // scope.cancelEdit(guild); + // expect(scope.groupCopy).to.eql({}); + // expect(guild._editing).to.eql(false); + }); + + describe('saveEdit', () => { + let guild; + + beforeEach(() => { + guild = specHelper.newGroup({ + _id: 'unique-guild-id', + name: 'old name', + leader: 'old leader', + type: 'guild', + members: ['not-user-id'], + $save: () => {}, + }); + + scope.editGroup(guild); + }); + + it('calls group.save', () => { + let guildSave = sandbox.spy(scope.groupCopy, '$save'); + + scope.saveEdit(guild); + + expect(guildSave).to.be.calledOnce; + }); + + it('calls cancelEdit', () => { + sandbox.stub(scope, 'cancelEdit'); + + scope.saveEdit(guild); + + expect(scope.cancelEdit).to.be.calledOnce; + }); + + it('applies changes to groupCopy to original group', () => { + scope.groupCopy.name = 'new name'; + + scope.saveEdit(guild); + + expect(guild.name).to.eql('new name'); + }); + + it('assigns leader id to group if leader has changed', () => { + scope.groupCopy._newLeader = { _id: 'some leader id' }; + + scope.saveEdit(guild); + + expect(guild.leader).to.eql('some leader id'); + }); + + it('does not assign new leader id if leader object is not passed in', () => { + scope.groupCopy._newLeader = 'not an object'; + + scope.saveEdit(guild); + + expect(guild.leader).to.eql('old leader'); + }); + }); + + describe('cancelEdit', () => { + beforeEach(() => { + guild = specHelper.newGroup({ + _id: 'unique-guild-id', + name: 'old name', + leader: 'old leader', + type: 'guild', + members: ['not-user-id'], + $save: () => {}, + }); + + scope.editGroup(guild); + }); + + it('sets _editing to false on group', () => { + expect(guild._editing).to.eql(true); + + scope.cancelEdit(guild); + + expect(guild._editing).to.eql(false); + }); + + it('reset groupCopy to an empty object', () => { + expect(scope.groupCopy).to.not.eql({}); + + scope.cancelEdit(guild); + + expect(scope.groupCopy).to.eql({}); + }); + }); + + /* TODO: Modal testing */ + describe.skip("deleteAllMessages", function() { }); + describe.skip("clickMember", function() { }); + describe.skip("removeMember", function() { }); + describe.skip("confirmRemoveMember", function() { }); + describe.skip("openInviteModal", function() { }); + describe.skip("quickReply", function() { }); }); diff --git a/website/public/js/controllers/groupsCtrl.js b/website/public/js/controllers/groupsCtrl.js index a6044d79f5..e7865afb55 100644 --- a/website/public/js/controllers/groupsCtrl.js +++ b/website/public/js/controllers/groupsCtrl.js @@ -40,11 +40,31 @@ habitrpg.controller("GroupsCtrl", ['$scope', '$rootScope', 'Shared', 'Groups', ' $scope.Members = Members; $scope._editing = {group:false}; + $scope.groupCopy = {}; + + $scope.editGroup = function (group) { + angular.copy(group, $scope.groupCopy); + group._editing = true; + }; + + + $scope.saveEdit = function (group) { + var newLeader = $scope.groupCopy._newLeader && $scope.groupCopy._newLeader._id; + + if (newLeader) { + $scope.groupCopy.leader = newLeader; + } + + angular.copy($scope.groupCopy, group); - $scope.save = function(group){ - if(group._newLeader && group._newLeader._id) group.leader = group._newLeader._id; group.$save(); + + $scope.cancelEdit(group); + }; + + $scope.cancelEdit = function (group) { group._editing = false; + $scope.groupCopy = {}; }; $scope.deleteAllMessages = function() { diff --git a/website/views/options/social/group.jade b/website/views/options/social/group.jade index b442f61e0c..9760198a94 100644 --- a/website/views/options/social/group.jade +++ b/website/views/options/social/group.jade @@ -18,34 +18,35 @@ a.pull-right.gem-wallet(ng-if='group.type!="party"', popover-trigger='mouseenter h3.panel-title span {{group.name}} span.group-leave-join(ng-if='group') - a.btn.btn-sm.btn-danger.pull-right(ng-if=":: isMemberOfGroup(User.user._id, group)", ng-click='clickLeave(group, $event)') + a.btn.btn-sm.btn-danger.pull-right(ng-if=":: isMemberOfGroup(User.user._id, group)", ng-hide='group._editing', ng-click='clickLeave(group, $event)') span.glyphicon.glyphicon-ban-circle =env.t('leave') a.btn.btn-success.pull-right(ng-if=':: !isMemberOfGroup(User.user._id, group)', ng-click='join(group)')=env.t('join') span(ng-if='group.leader._id == user.id') - button.btn.btn-sm.btn-primary.pull-right(ng-click='save(group)', ng-show='group._editing')=env.t('save') - button.btn.btn-sm.btn-default.pull-right(ng-click='group._editing = true', ng-hide='group._editing')=env.t('editGroup') + button.btn.btn-sm.btn-primary.pull-right(ng-click='cancelEdit(group)', ng-hide='!group._editing')=env.t('cancel') + button.btn.btn-sm.btn-primary.pull-right(ng-click='saveEdit(group)', ng-show='group._editing')=env.t('save') + button.btn.btn-sm.btn-default.pull-right(ng-click='editGroup(group)', ng-hide='group._editing')=env.t('editGroup') .panel-body form(ng-show='group._editing') .form-group label=env.t('groupName') - input.form-control(type='text', ng-model='group.name', placeholder=env.t('groupName')) + input.form-control(type='text', ng-model='groupCopy.name', placeholder=env.t('groupName')) .form-group label=env.t('description') - textarea.form-control(rows=6, ng-model='group.description') + textarea.form-control(rows=6, ng-model='groupCopy.description') include ../../shared/formatting-help .form-group label=env.t('logoUrl') - input.form-control(type='url', placeholder=env.t('logoUrl'), ng-model='group.logo') + input.form-control(type='url', placeholder=env.t('logoUrl'), ng-model='groupCopy.logo') .form-group .checkbox label - input(type='checkbox', ng-model='group.leaderOnly.challenges') + input(type='checkbox', ng-model='groupCopy.leaderOnly.challenges') =env.t('leaderOnlyChallenges') h4=env.t('assignLeader') - select#group-leader-selection(ng-model='group._newLeader', ng-options='member.profile.name for member in group.members') + select#group-leader-selection(ng-model='groupCopy._newLeader', ng-options='member.profile.name for member in group.members') div(ng-show='!group._editing') img.img-rendering-auto.pull-right(ng-show='group.logo', ng-src='{{group.logo}}') @@ -131,7 +132,7 @@ a.pull-right.gem-wallet(ng-if='group.type!="party"', popover-trigger='mouseenter .col-md-8 div - textarea.form-control(ng-show='group._editing', rows=6, placeholder=env.t('leaderMsg'), ng-model='group.leaderMessage') + textarea.form-control(ng-show='group._editing', rows=6, placeholder=env.t('leaderMsg'), ng-model='groupCopy.leaderMessage') .slight-vertical-padding table(ng-show='group.leaderMessage') tr @@ -140,7 +141,7 @@ a.pull-right.gem-wallet(ng-if='group.type!="party"', popover-trigger='mouseenter .arrow h3.popover-title {{group.leader.profile.name}} .popover-content - markdown(text='group.leaderMessage') + markdown(text='group._editing ? groupCopy.leaderMessage : group.leaderMessage') div(ng-controller='ChatCtrl') h3=env.t('chat') include ./chat-box