Skip to content
This repository was archived by the owner on Sep 5, 2024. It is now read-only.

Commit e898d22

Browse files
devversionThomasBurleson
authored andcommitted
fix(dialog): apply foreground color and automatically detect theme
* Apply the missing foreground color on the md-dialog element * Automatically detect the theme from the `targetEvent` property. - Developers are still able to overwrite the theme (as before) - Theme will fallback to the default theme (as before) - If `targetEvent` is specified, it will use the `mdTheme` controller to lookup for a changed theme Fixes #8719. Closes #8723
1 parent 6e011b9 commit e898d22

File tree

5 files changed

+100
-4
lines changed

5 files changed

+100
-4
lines changed

src/components/dialog/dialog-theme.scss

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,10 @@ $dialog-border-radius: 4px !default;
22

33
md-dialog.md-THEME_NAME-theme {
44
border-radius: $dialog-border-radius;
5+
56
background-color: '{{background-hue-1}}';
7+
color: '{{foreground-1}}';
8+
69

710
&.md-content-overflow {
811
.md-actions, md-dialog-actions {

src/components/dialog/dialog.js

Lines changed: 30 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -551,7 +551,7 @@ function MdDialogProvider($$interimElementProvider) {
551551
});
552552

553553
/* @ngInject */
554-
function advancedDialogOptions($mdDialog, $mdTheming, $mdConstant) {
554+
function advancedDialogOptions($mdDialog, $mdConstant) {
555555
return {
556556
template: [
557557
'<md-dialog md-theme="{{ dialog.theme }}" aria-label="{{ dialog.ariaLabel }}" ng-class="dialog.css">',
@@ -599,15 +599,17 @@ function MdDialogProvider($$interimElementProvider) {
599599
},
600600
controllerAs: 'dialog',
601601
bindToController: true,
602-
theme: $mdTheming.defaultTheme()
603602
};
604603
}
605604

606605
/* @ngInject */
607-
function dialogDefaultOptions($mdDialog, $mdAria, $mdUtil, $mdConstant, $animate, $document, $window, $rootElement, $log, $injector) {
606+
function dialogDefaultOptions($mdDialog, $mdAria, $mdUtil, $mdConstant, $animate, $document, $window, $rootElement,
607+
$log, $injector, $mdTheming) {
608+
608609
return {
609610
hasBackdrop: true,
610611
isolateScope: true,
612+
onCompiling: beforeCompile,
611613
onShow: onShow,
612614
onShowing: beforeShow,
613615
onRemove: onRemove,
@@ -641,7 +643,15 @@ function MdDialogProvider($$interimElementProvider) {
641643
}
642644
};
643645

646+
function beforeCompile(options) {
647+
// Automatically apply the theme, if the user didn't specify a theme explicitly.
648+
// Those option changes need to be done, before the compilation has started, because otherwise
649+
// the option changes will be not available in the $mdCompilers locales.
650+
detectTheming(options);
651+
}
652+
644653
function beforeShow(scope, element, options, controller) {
654+
645655
if (controller) {
646656
controller.mdHtmlContent = controller.htmlContent || options.htmlContent || '';
647657
controller.mdTextContent = controller.textContent || options.textContent ||
@@ -797,6 +807,22 @@ function MdDialogProvider($$interimElementProvider) {
797807
}
798808
}
799809

810+
function detectTheming(options) {
811+
// Only detect the theming, if the developer didn't specify the theme specifically.
812+
if (options.theme) return;
813+
814+
options.theme = $mdTheming.defaultTheme();
815+
816+
if (options.targetEvent && options.targetEvent.target) {
817+
var targetEl = angular.element(options.targetEvent.target);
818+
819+
// Once the user specifies a targetEvent, we will automatically try to find the correct
820+
// nested theme.
821+
options.theme = (targetEl.controller('mdTheme') || {}).$mdTheme || options.theme;
822+
}
823+
824+
}
825+
800826
/**
801827
* Capture originator/trigger/from/to element information (if available)
802828
* and the parent container for the dialog; defaults to the $rootElement
@@ -817,6 +843,7 @@ function MdDialogProvider($$interimElementProvider) {
817843
options.origin = getBoundingClientRect(options.targetEvent.target, options.origin);
818844
}
819845

846+
820847
/**
821848
* Identify the bounding RECT for the target element
822849
*

src/components/dialog/dialog.spec.js

Lines changed: 43 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -123,6 +123,49 @@ describe('$mdDialog', function() {
123123
expect(resolved).toBe(true);
124124
}));
125125

126+
it('should normally use the default theme', inject(function($animate, $rootScope, $mdDialog, $compile) {
127+
var dialogParent = angular.element('<div>');
128+
129+
$mdDialog.show(
130+
$mdDialog
131+
.alert()
132+
.parent(dialogParent)
133+
.title("Title")
134+
.textContent("Themed Dialog")
135+
.ok('Close')
136+
);
137+
138+
$rootScope.$apply();
139+
runAnimation();
140+
141+
var mdContainer = angular.element(dialogParent[0].querySelector('.md-dialog-container'));
142+
var mdDialog = mdContainer.find('md-dialog');
143+
144+
expect(mdDialog.attr('md-theme')).toBe('default');
145+
}));
146+
147+
it('should apply the specified theme', inject(function($animate, $rootScope, $mdDialog, $compile) {
148+
var dialogParent = angular.element('<div>');
149+
150+
$mdDialog.show(
151+
$mdDialog
152+
.alert()
153+
.parent(dialogParent)
154+
.title("Title")
155+
.theme('myTheme')
156+
.textContent("Themed Dialog")
157+
.ok('Close')
158+
);
159+
160+
$rootScope.$apply();
161+
runAnimation();
162+
163+
var mdContainer = angular.element(dialogParent[0].querySelector('.md-dialog-container'));
164+
var mdDialog = mdContainer.find('md-dialog');
165+
166+
expect(mdDialog.attr('md-theme')).toBe('myTheme');
167+
}));
168+
126169
it('should focus `md-dialog-content` on open', inject(function($mdDialog, $rootScope, $document) {
127170
jasmine.mockElementFocus(this);
128171

src/core/services/interimElement/interimElement.js

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -426,7 +426,11 @@ function InterimElementProvider() {
426426
* Use optional autoHided and transition-in effects
427427
*/
428428
function createAndTransitionIn() {
429-
return $q(function(resolve, reject){
429+
return $q(function(resolve, reject) {
430+
431+
// Trigger onCompiling callback before the compilation starts.
432+
// This is useful, when modifying options, which can be influenced by developers.
433+
options.onCompiling && options.onCompiling(options);
430434

431435
compileElement(options)
432436
.then(function( compiledData ) {

src/core/services/interimElement/interimElement.spec.js

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -387,6 +387,25 @@ describe('$$interimElement service', function() {
387387
expect(autoClosed).toBe(true);
388388
}));
389389

390+
it('calls onCompiling before onShowing', inject(function() {
391+
var onCompilingCalled = false;
392+
393+
Service.show({
394+
template: '<div>My Element</div>',
395+
onCompiling: beforeCompile,
396+
onShowing: beforeShow
397+
});
398+
399+
function beforeCompile() {
400+
onCompilingCalled = true;
401+
}
402+
403+
function beforeShow() {
404+
expect(onCompilingCalled).toBe(true);
405+
}
406+
407+
}));
408+
390409
it('calls onShowing before onShow', inject(function() {
391410
var onShowingCalled = false;
392411

0 commit comments

Comments
 (0)