Skip to content

Commit 708fc03

Browse files
committed
restructured, improved gulp, angry about not optional focus sets in bottom sheet
1 parent 7e5b553 commit 708fc03

11 files changed

+2383
-2235
lines changed

dist/mdKeyboard.js

Lines changed: 1109 additions & 1042 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

dist/mdKeyboard.min.js

Lines changed: 3 additions & 3 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

gulpfile.js

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,10 @@ var gulp = require('gulp'),
22
path = require('path'),
33
jshintReporter = require('jshint-stylish'),
44
plugins = require('gulp-load-plugins')({
5-
config: path.join(__dirname, 'package.json')
5+
config: path.join(__dirname, 'package.json'),
6+
rename: {
7+
'gulp-angular-embed-templates': 'embedTemplates'
8+
}
69
});
710

811
var sctiptPath = {
@@ -41,11 +44,16 @@ gulp.task('build', function () {
4144

4245
gulp
4346
.src([
44-
'src/js/mdKeyboard.js'
47+
'src/js/mdKeyboard.module.js',
48+
'src/js/mdKeyboard.layouts.js',
49+
'src/js/mdKeyboard.deadkey.js',
50+
'src/js/mdKeyboard.provider.js',
51+
'src/js/mdKeyboard.directive.js'
4552
])
4653
.pipe(plugins.concat('mdKeyboard.js'))
4754
.pipe(plugins.header(header, {pkg: pkg}))
4855
.pipe(plugins.footer(footer))
56+
.pipe(plugins.embedTemplates())
4957
.pipe(plugins.replace(/[\r\n]+\s*\/\/.*TODO:+.*/gi, ''))
5058
.pipe(gulp.dest('./dist/'))
5159
.pipe(plugins.uglify())

package.json

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,13 +9,14 @@
99
"bower": "^1.7.7",
1010
"conventional-changelog": "0.0.16",
1111
"gulp": "^3.8.11",
12+
"gulp-angular-embed-templates": "^2.1.2",
1213
"gulp-concat": "^2.5.2",
1314
"gulp-footer": "^1.0.5",
1415
"gulp-header": "^1.2.2",
1516
"gulp-jshint": "^1.9.2",
1617
"gulp-load-plugins": "^0.8.0",
17-
"gulp-uglify": "^1.1.0",
1818
"gulp-replace": "^0.5.4",
19+
"gulp-uglify": "^1.1.0",
1920
"jshint-stylish": "^1.0.0"
2021
},
2122
"directories": {},

src/js/mdKeyboard.deadkey.js

Lines changed: 209 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,209 @@
1+
// - Lay out each dead key set as an object of property/value
2+
// pairs. The rows below are wrapped so uppercase letters are
3+
// below their lowercase equivalents.
4+
//
5+
// - The property name is the letter pressed after the diacritic.
6+
// The property value is the letter this key-combo will generate.
7+
//
8+
// - Note that if you have created a new keyboard layout and want
9+
// it included in the distributed script, PLEASE TELL ME if you
10+
// have added additional dead keys to the ones below.
11+
12+
angular
13+
.module('mdKeyboard')
14+
.constant('keyboardDeadkey', (function () {
15+
var deadkey = {
16+
'"': {
17+
'a': "\u00e4",
18+
'e': "\u00eb",
19+
'i': "\u00ef",
20+
'o': "\u00f6",
21+
'u': "\u00fc",
22+
'y': "\u00ff",
23+
'\u03b9': "\u03ca",
24+
'\u03c5': "\u03cb",
25+
'\u016B': "\u01D6",
26+
'\u00FA': "\u01D8",
27+
'\u01D4': "\u01DA",
28+
'\u00F9': "\u01DC",
29+
'A': "\u00c4",
30+
'E': "\u00cb",
31+
'I': "\u00cf",
32+
'O': "\u00d6",
33+
'U': "\u00dc",
34+
'Y': "\u0178",
35+
'\u0399': "\u03aa",
36+
'\u03a5': "\u03ab",
37+
'\u016A': "\u01D5",
38+
'\u00DA': "\u01D7",
39+
'\u01D3': "\u01D9",
40+
'\u00D9': "\u01DB",
41+
'\u304b': "\u304c",
42+
'\u304d': "\u304e",
43+
'\u304f': "\u3050",
44+
'\u3051': "\u3052",
45+
'\u3053': "\u3054",
46+
'\u305f': "\u3060",
47+
'\u3061': "\u3062",
48+
'\u3064': "\u3065",
49+
'\u3066': "\u3067",
50+
'\u3068': "\u3069",
51+
'\u3055': "\u3056",
52+
'\u3057': "\u3058",
53+
'\u3059': "\u305a",
54+
'\u305b': "\u305c",
55+
'\u305d': "\u305e",
56+
'\u306f': "\u3070",
57+
'\u3072': "\u3073",
58+
'\u3075': "\u3076",
59+
'\u3078': "\u3079",
60+
'\u307b': "\u307c",
61+
'\u30ab': "\u30ac",
62+
'\u30ad': "\u30ae",
63+
'\u30af': "\u30b0",
64+
'\u30b1': "\u30b2",
65+
'\u30b3': "\u30b4",
66+
'\u30bf': "\u30c0",
67+
'\u30c1': "\u30c2",
68+
'\u30c4': "\u30c5",
69+
'\u30c6': "\u30c7",
70+
'\u30c8': "\u30c9",
71+
'\u30b5': "\u30b6",
72+
'\u30b7': "\u30b8",
73+
'\u30b9': "\u30ba",
74+
'\u30bb': "\u30bc",
75+
'\u30bd': "\u30be",
76+
'\u30cf': "\u30d0",
77+
'\u30d2': "\u30d3",
78+
'\u30d5': "\u30d6",
79+
'\u30d8': "\u30d9",
80+
'\u30db': "\u30dc"
81+
},
82+
'~': { // Tilde / Stroke
83+
'a': "\u00e3", 'l': "\u0142", 'n': "\u00f1", 'o': "\u00f5",
84+
'A': "\u00c3", 'L': "\u0141", 'N': "\u00d1", 'O': "\u00d5"
85+
},
86+
'^': { // Circumflex
87+
'a': "\u00e2", 'e': "\u00ea", 'i': "\u00ee", 'o': "\u00f4", 'u': "\u00fb", 'w': "\u0175", 'y': "\u0177",
88+
'A': "\u00c2", 'E': "\u00ca", 'I': "\u00ce", 'O': "\u00d4", 'U': "\u00db", 'W': "\u0174", 'Y': "\u0176"
89+
},
90+
'\u02c7': { // Baltic caron
91+
'c': "\u010D",
92+
'd': "\u010f",
93+
'e': "\u011b",
94+
's': "\u0161",
95+
'l': "\u013e",
96+
'n': "\u0148",
97+
'r': "\u0159",
98+
't': "\u0165",
99+
'u': "\u01d4",
100+
'z': "\u017E",
101+
'\u00fc': "\u01da",
102+
'C': "\u010C",
103+
'D': "\u010e",
104+
'E': "\u011a",
105+
'S': "\u0160",
106+
'L': "\u013d",
107+
'N': "\u0147",
108+
'R': "\u0158",
109+
'T': "\u0164",
110+
'U': "\u01d3",
111+
'Z': "\u017D",
112+
'\u00dc': "\u01d9"
113+
},
114+
'\u02d8': { // Romanian and Turkish breve
115+
'a': "\u0103", 'g': "\u011f",
116+
'A': "\u0102", 'G': "\u011e"
117+
},
118+
'-': { // Macron
119+
'a': "\u0101",
120+
'e': "\u0113",
121+
'i': "\u012b",
122+
'o': "\u014d",
123+
'u': "\u016B",
124+
'y': "\u0233",
125+
'\u00fc': "\u01d6",
126+
'A': "\u0100",
127+
'E': "\u0112",
128+
'I': "\u012a",
129+
'O': "\u014c",
130+
'U': "\u016A",
131+
'Y': "\u0232",
132+
'\u00dc': "\u01d5"
133+
},
134+
'`': { // Grave
135+
'a': "\u00e0", 'e': "\u00e8", 'i': "\u00ec", 'o': "\u00f2", 'u': "\u00f9", '\u00fc': "\u01dc",
136+
'A': "\u00c0", 'E': "\u00c8", 'I': "\u00cc", 'O': "\u00d2", 'U': "\u00d9", '\u00dc': "\u01db"
137+
},
138+
"'": { // Acute / Greek Tonos
139+
'a': "\u00e1",
140+
'e': "\u00e9",
141+
'i': "\u00ed",
142+
'o': "\u00f3",
143+
'u': "\u00fa",
144+
'y': "\u00fd",
145+
'\u03b1': "\u03ac",
146+
'\u03b5': "\u03ad",
147+
'\u03b7': "\u03ae",
148+
'\u03b9': "\u03af",
149+
'\u03bf': "\u03cc",
150+
'\u03c5': "\u03cd",
151+
'\u03c9': "\u03ce",
152+
'\u00fc': "\u01d8",
153+
'A': "\u00c1",
154+
'E': "\u00c9",
155+
'I': "\u00cd",
156+
'O': "\u00d3",
157+
'U': "\u00da",
158+
'Y': "\u00dd",
159+
'\u0391': "\u0386",
160+
'\u0395': "\u0388",
161+
'\u0397': "\u0389",
162+
'\u0399': "\u038a",
163+
'\u039f': "\u038c",
164+
'\u03a5': "\u038e",
165+
'\u03a9': "\u038f",
166+
'\u00dc': "\u01d7"
167+
},
168+
'\u02dd': {// Hungarian Double Acute Accent
169+
'o': "\u0151", 'u': "\u0171",
170+
'O': "\u0150", 'U': "\u0170"
171+
},
172+
'\u0385': { // Greek Dialytika + Tonos
173+
'\u03b9': "\u0390", '\u03c5': "\u03b0"
174+
},
175+
'\u00b0': { // Ring
176+
'a': "\u00e5", 'u': "\u016f",
177+
'A': "\u00c5", 'U': "\u016e"
178+
},
179+
'\u02DB': { // Ogonek
180+
'a': "\u0106", 'e': "\u0119", 'i': "\u012f", 'o': "\u01eb", 'u': "\u0173", 'y': "\u0177",
181+
'A': "\u0105", 'E': "\u0118", 'I': "\u012e", 'O': "\u01ea", 'U': "\u0172", 'Y': "\u0176"
182+
},
183+
'\u02D9': { // Dot-above
184+
'c': "\u010B", 'e': "\u0117", 'g': "\u0121", 'z': "\u017C",
185+
'C': "\u010A", 'E': "\u0116", 'G': "\u0120", 'Z': "\u017B"
186+
},
187+
'\u00B8': { // Cedilla
188+
'c': "\u00e7", 's': "\u015F",
189+
'C': "\u00c7", 'S': "\u015E"
190+
},
191+
/*',': { // Comma
192+
's': (this.VKI_isIElt8) ? "\u015F" : "\u0219", 't': (this.VKI_isIElt8) ? "\u0163" : "\u021B",
193+
'S': (this.VKI_isIElt8) ? "\u015E" : "\u0218", 'T': (this.VKI_isIElt8) ? "\u0162" : "\u021A"
194+
},*/
195+
'\u3002': { // Hiragana/Katakana Point
196+
'\u306f': "\u3071", '\u3072': "\u3074", '\u3075': "\u3077", '\u3078': "\u307a", '\u307b': "\u307d",
197+
'\u30cf': "\u30d1", '\u30d2': "\u30d4", '\u30d5': "\u30d7", '\u30d8': "\u30da", '\u30db': "\u30dd"
198+
}
199+
};
200+
201+
// aliases
202+
deadkey['\u00af'] = deadkey['-']; // Macron
203+
deadkey['\u00a8'] = deadkey['\u309B'] = deadkey['"']; // Umlaut / Diaeresis / Greek Dialytika / Hiragana/Katakana Voiced Sound Mark
204+
deadkey['\u00b4'] = deadkey['\u0384'] = deadkey["'"]; // Acute / Greek Tonos
205+
deadkey['\u00ba'] = deadkey['\u00b0']; // Ring
206+
deadkey['\u201a'] = deadkey['\u00B8'];
207+
208+
return deadkey;
209+
})());

src/js/mdKeyboard.directive.js

Lines changed: 135 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,135 @@
1+
angular
2+
.module('mdKeyboard')
3+
.directive('mdKeyboard', MdKeyboardDirective);
4+
5+
function MdKeyboardDirective($injector, $animate, $mdConstant, $mdUtil, $mdTheming, $mdBottomSheet, $rootElement, $mdGesture) {
6+
return {
7+
restrict: 'A',
8+
require: '?ngModel',
9+
scope: {
10+
clickOutsideToClose: '=',
11+
escapeToClose: '=',
12+
preserveScope: '=',
13+
showInMobile: '=',
14+
useBackdrop: '='
15+
},
16+
link: function (scope, element, attrs, ngModelCtrl) {
17+
if (!ngModelCtrl) {
18+
return;
19+
}
20+
21+
var bottomSheet;
22+
23+
// Don't show virtual keyboard in mobile devices (default)
24+
//TODO: test detection and reimplement if neccessary
25+
//TODO: dissolve dependency to UAParser if possible / use angular or material utils
26+
if ($injector.has('UAParser')) {
27+
var UAParser = $injector.get('UAParser');
28+
var results = new UAParser().getResult();
29+
var isMobile = results.device.type === 'mobile' || results.device.type === 'tablet';
30+
isMobile = isMobile || (results.os && (results.os.name === 'Android'));
31+
isMobile = isMobile || (results.os && (results.os.name === 'iOS'));
32+
isMobile = isMobile || (results.os && (results.os.name === 'Windows Phone'));
33+
isMobile = isMobile || (results.os && (results.os.name === 'Windows Mobile'));
34+
if (isMobile && attrs.showInMobile !== true) {
35+
return;
36+
}
37+
}
38+
39+
/*
40+
ngVirtualKeyboardService.attach(elements[0], scope.config, function() {
41+
$timeout(function() {
42+
ngModelCtrl.$setViewValue(elements[0].value);
43+
});
44+
});
45+
*/
46+
47+
// open bottomsheet with keyboard on focus TODO: and without backdrop
48+
element
49+
.bind('focus', showKeyboard)
50+
.bind('blur', hideKeyboard);
51+
52+
function showKeyboard() {
53+
bottomSheet = $mdBottomSheet.show({
54+
templateUrl: '../view/mdKeyboard.view.html',
55+
controller: KeyboardController,
56+
clickOutsideToClose: attrs.clickOutsideToClose || false,
57+
escapeToClose: attrs.escapeToClose || false,
58+
preserveScope: attrs.preserveScope || true,
59+
useBackdrop: attrs.useBackdrop || false,
60+
onShow: onShowKeyboard
61+
});
62+
}
63+
64+
function hideKeyboard() {
65+
if (bottomSheet) {
66+
$mdBottomSheet.hide();
67+
bottomSheet = undefined;
68+
}
69+
}
70+
71+
function onShowKeyboard(scope, element, options, controller) {
72+
$log.debug(element);
73+
element = $mdUtil.extractElementByName(element, 'md-bottom-sheet');
74+
75+
// Add a backdrop that will close on click
76+
backdrop = $mdUtil.createBackdrop(scope, "md-bottom-sheet-backdrop md-opaque");
77+
78+
if (options.clickOutsideToClose) {
79+
backdrop.on('click', function () {
80+
$mdUtil.nextTick($mdBottomSheet.cancel, true);
81+
});
82+
}
83+
84+
$mdTheming.inherit(backdrop, options.parent);
85+
86+
$animate.enter(backdrop, options.parent, null);
87+
88+
var bottomSheet = new BottomSheet(element, options.parent);
89+
options.bottomSheet = bottomSheet;
90+
91+
$mdTheming.inherit(bottomSheet.element, options.parent);
92+
93+
if (options.disableParentScroll) {
94+
options.restoreScroll = $mdUtil.disableScrollAround(bottomSheet.element, options.parent);
95+
}
96+
97+
return $animate
98+
.enter(bottomSheet.element, options.parent)
99+
.then(function () {
100+
var focusable = $mdUtil.findFocusTarget(element) || angular.element(
101+
element[0].querySelector('button') ||
102+
element[0].querySelector('a') ||
103+
element[0].querySelector('[ng-click]')
104+
);
105+
focusable.focus();
106+
107+
if (options.escapeToClose) {
108+
options.rootElementKeyupCallback = function (e) {
109+
if (e.keyCode === $mdConstant.KEY_CODE.ESCAPE) {
110+
$mdUtil.nextTick($mdBottomSheet.cancel, true);
111+
}
112+
};
113+
$rootElement.on('keyup', options.rootElementKeyupCallback);
114+
}
115+
});
116+
}
117+
118+
function KeyboardController($scope, $log, mdKeyboard) {
119+
//element.blur();
120+
//element.focus();
121+
122+
$scope.keyboard = mdKeyboard.getLayout();
123+
$scope.pressed = function ($event) {
124+
$log.debug($event);
125+
}
126+
}
127+
128+
// When navigation force destroys an element, then
129+
// listen and hide the keyboard...
130+
scope.$on('$destroy', function () {
131+
hideKeyboard();
132+
});
133+
}
134+
}
135+
}

0 commit comments

Comments
 (0)