Skip to content

Commit 87cda03

Browse files
committed
#14 improve the case merge dialog to support autocomplete, search by title and by case number
1 parent 05be4c4 commit 87cda03

File tree

3 files changed

+75
-27
lines changed

3 files changed

+75
-27
lines changed
Original file line numberDiff line numberDiff line change
@@ -1,38 +1,69 @@
1-
(function() {
1+
(function () {
22
'use strict';
33

44
angular.module('theHiveControllers')
55
.controller('CaseMergeModalCtrl', CaseMergeModalCtrl);
66

7-
function CaseMergeModalCtrl($state, $modalInstance, SearchSrv, CaseSrv, UserInfoSrv, AlertSrv, caze) {
7+
function CaseMergeModalCtrl($state, $modalInstance, $q, SearchSrv, CaseSrv, UserInfoSrv, AlertSrv, caze, $http) {
88
var me = this;
99

1010
this.caze = caze;
11+
this.pendingAsync = false;
1112
this.search = {
12-
caseId: null,
13+
type: 'title',
14+
placeholder: 'Search by case title',
15+
minInputLength: 1,
16+
input: null,
1317
cases: []
1418
};
1519
this.getUserInfo = UserInfoSrv;
1620

17-
this.getCaseByNumber = function() {
18-
if (this.search.caseId && this.search.caseId !== this.caze.caseId) {
19-
SearchSrv(function(data /*, total*/ ) {
20-
console.log(data);
21-
me.search.cases = data;
22-
}, {
23-
_string: 'caseId:' + me.search.caseId
24-
}, 'case', 'all');
25-
} else {
26-
this.search.cases = [];
21+
this.getCaseByTitle = function(type, input) {
22+
var defer = $q.defer();
23+
24+
SearchSrv(function (data /*, total*/ ) {
25+
defer.resolve(data);
26+
}, {
27+
_string: (type === 'title') ? ('title:"' + input + '"') : ('caseId:' + input)
28+
}, 'case', 'all');
29+
30+
return defer.promise;
31+
}
32+
33+
this.format = function(caze) {
34+
if(caze) {
35+
return '#' + caze.caseId + ' - ' + caze.title;
2736
}
28-
};
37+
return null;
38+
}
39+
40+
this.clearSearch = function() {
41+
this.search.input = null;
42+
this.search.cases = [];
43+
}
44+
45+
this.onTypeChange = function(type) {
46+
this.clearSearch();
2947

30-
this.merge = function() {
48+
this.search.placeholder = 'Search by case ' + type;
49+
50+
if(type === 'title') {
51+
this.search.minInputLength = 3;
52+
} else if(type === 'number') {
53+
this.search.minInputLength = 1;
54+
}
55+
}
56+
57+
this.onSelect = function(item, model, label) {
58+
this.search.cases = [item];
59+
}
60+
61+
this.merge = function () {
3162
// TODO pass params as path params not query params
3263
CaseSrv.merge({}, {
3364
caseId: me.caze.id,
3465
mergedCaseId: me.search.cases[0].id
35-
}, function(merged) {
66+
}, function (merged) {
3667

3768
$state.go('app.case.details', {
3869
caseId: merged.id
@@ -41,13 +72,13 @@
4172
$modalInstance.dismiss();
4273

4374
AlertSrv.log('The cases have been successfully merged into a new case #' + merged.caseId, 'success');
44-
}, function(response){
75+
}, function (response) {
4576
AlertSrv.error('CaseMergeModalCtrl', response.data, response.status);
4677
});
4778
};
4879

49-
this.cancel = function() {
80+
this.cancel = function () {
5081
$modalInstance.dismiss();
51-
};
82+
};
5283
}
5384
})();

ui/app/styles/case.css

+5
Original file line numberDiff line numberDiff line change
@@ -56,3 +56,8 @@ span.link-id {
5656
padding: 10px;
5757
overflow: hidden;
5858
}
59+
60+
.merge-dialog .search-field ul.dropdown-menu {
61+
width: 100%;
62+
left: 0 !important;
63+
}

ui/app/views/partials/case/case.merge.html

+20-8
Original file line numberDiff line numberDiff line change
@@ -2,12 +2,25 @@
22
<h3 class="modal-title">Merge Case #{{dialog.caze.caseId}}</h3>
33
</div>
44
<div class="modal-body merge-dialog">
5-
<div class="input-group input-group-lg">
6-
<span class="input-group-addon">#</span>
7-
<input type="text" class="form-control" placeholder="Case number" ng-model-options='{ debounce: 500 }' ng-change="dialog.getCaseByNumber()" ng-model="dialog.search.caseId">
5+
<div class="input-group input-group-lg search-field">
6+
<input type="text"
7+
placeholder="{{dialog.search.placeholder}}"
8+
ng-model="dialog.search.input"
9+
typeahead-wait-ms="500"
10+
typeahead="caze as dialog.format(caze) for caze in dialog.getCaseByTitle(dialog.search.type, $viewValue)"
11+
typeahead-min-length="dialog.search.minInputLength"
12+
typeahead-on-select="dialog.onSelect($item)"
13+
class="form-control">
14+
15+
<span class="input-group-addon">
16+
<input type="radio" name="search-type" ng-model="dialog.search.type" value="title" ng-change="dialog.onTypeChange('title')"> By Title
17+
<input type="radio" name="search-type" ng-model="dialog.search.type" value="number" ng-change="dialog.onTypeChange('number')"> By Number
18+
</span>
19+
820
</div>
21+
922
<div class="empty-message mv-s" ng-show="dialog.search.cases.length === 0">
10-
Please search for the to be merged with
23+
Please search for the case to be merged with <br>
1124
<strong>#{{dialog.caze.caseId}}:
1225
{{dialog.caze.title}}</strong>
1326
</div>
@@ -18,11 +31,10 @@ <h4>{{c.title}}</h4>
1831
<i class="glyphicon glyphicon-user"></i>
1932
<span ng-bind="dialog.getUserInfo(c.user) | getField: 'name'"></span>
2033
</span>
21-
2234
<span class="ml-xxs">
2335
<i class="glyphicon glyphicon-calendar"></i>
2436
<span>{{c.startDate | showDate}}</span>&nbsp;&nbsp;
25-
<span ng-show="isCaseClosed()" class="text-success">(Closed at
37+
<span ng-show="isCaseClosed()" class="text-success">(Closed at
2638
{{c.endDate | showDate}}
2739
as
2840
<strong>{{CaseResolutionStatus[c.resolutionStatus]}}</strong>)</span>
@@ -32,13 +44,13 @@ <h4>{{c.title}}</h4>
3244
<strong>Tags:</strong>
3345
<tag-list data="c.tags"></tag-list>
3446
</div>
35-
3647
<div class="mt-xs wrap">
3748
<div marked="c.description" class="markdown"></div>
3849
</div>
3950
</div>
4051
</div>
4152
<div class="modal-footer text-left">
4253
<button class="btn btn-default" ng-click="dialog.cancel()" type="button">Cancel</button>
43-
<button class="btn btn-primary pull-right" ng-click="dialog.merge()" type="button">Merge</button>
54+
<button class="btn btn-primary pull-right" ng-click="dialog.merge()" ng-disabled="dialog.pendingAsync || dialog.search.cases.length < 1"
55+
type="button">Merge</button>
4456
</div>

0 commit comments

Comments
 (0)