mirror of https://github.com/apache/nifi.git
[NIFI-13226] - Support changing color of processors and labels (#8836)
* [NIFI-13226] - Support changing color of processors and labels * style the processor icon for better support cross-themes This closes #8836
This commit is contained in:
parent
15ac906725
commit
60112f242c
|
@ -29,6 +29,7 @@ import {
|
|||
navigateToEditComponent,
|
||||
navigateToEditCurrentProcessGroup,
|
||||
navigateToManageComponentPolicies,
|
||||
openChangeColorDialog,
|
||||
paste,
|
||||
reloadFlow,
|
||||
selectComponents,
|
||||
|
@ -38,6 +39,7 @@ import {
|
|||
stopCurrentProcessGroup
|
||||
} from '../state/flow/flow.actions';
|
||||
import {
|
||||
ChangeColorRequest,
|
||||
CopyComponentRequest,
|
||||
DeleteComponentRequest,
|
||||
DisableComponentRequest,
|
||||
|
@ -422,6 +424,34 @@ export class CanvasActionsService {
|
|||
})
|
||||
);
|
||||
}
|
||||
},
|
||||
changeColor: {
|
||||
id: 'changeColor',
|
||||
condition: (selection: d3.Selection<any, any, any, any>) => {
|
||||
return this.canvasUtils.isColorable(selection);
|
||||
},
|
||||
action: (selection: d3.Selection<any, any, any, any>) => {
|
||||
const changeColorRequests: ChangeColorRequest[] = [];
|
||||
selection.each((d) => {
|
||||
let color = null;
|
||||
if (d.component.style) {
|
||||
color = d.component.style['background-color'] || null;
|
||||
}
|
||||
changeColorRequests.push({
|
||||
id: d.id,
|
||||
uri: d.uri,
|
||||
type: d.type,
|
||||
color,
|
||||
style: d.component.style || null,
|
||||
revision: this.client.getRevision(d)
|
||||
});
|
||||
});
|
||||
this.store.dispatch(
|
||||
openChangeColorDialog({
|
||||
request: changeColorRequests
|
||||
})
|
||||
);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
|
|
|
@ -1161,15 +1161,10 @@ export class CanvasContextMenu implements ContextMenuDefinitionProvider {
|
|||
}
|
||||
},
|
||||
{
|
||||
condition: (selection: any) => {
|
||||
// TODO - isColorable
|
||||
return false;
|
||||
},
|
||||
condition: this.canvasActionsService.getConditionFunction('changeColor'),
|
||||
clazz: 'fa fa-paint-brush',
|
||||
text: 'Change Color',
|
||||
action: () => {
|
||||
// TODO - fillColor
|
||||
}
|
||||
action: this.canvasActionsService.getActionFunction('changeColor')
|
||||
},
|
||||
{
|
||||
condition: (selection: d3.Selection<any, any, any, any>) => {
|
||||
|
|
|
@ -2028,4 +2028,30 @@ export class CanvasUtils {
|
|||
|
||||
return this.isConnection(selection) || this.isLabel(selection);
|
||||
}
|
||||
|
||||
public isColorable(selection: d3.Selection<any, any, any, any>) {
|
||||
if (selection.empty()) {
|
||||
return false;
|
||||
}
|
||||
|
||||
// require read and write permissions
|
||||
if (!this.canRead(selection) || !this.canModify(selection)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
// determine if the current selection is entirely processors or labels
|
||||
const selectedProcessors = selection.filter((d, index, nodes) => {
|
||||
const processor = d3.select(nodes[index]);
|
||||
return this.isProcessor(processor) && this.canModify(processor);
|
||||
});
|
||||
const selectedLabels = selection.filter((d, index, nodes) => {
|
||||
const label = d3.select(nodes[index]);
|
||||
return this.isLabel(label) && this.canModify(label);
|
||||
});
|
||||
|
||||
const allProcessors = selectedProcessors.size() === selection.size();
|
||||
const allLabels = selectedLabels.size() === selection.size();
|
||||
|
||||
return allProcessors || allLabels;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -648,9 +648,12 @@ export class ProcessorManager {
|
|||
});
|
||||
}
|
||||
} else {
|
||||
// undo changes made above
|
||||
processor.select('text.processor-icon').attr('class', () => {
|
||||
return 'processor-icon accent-color';
|
||||
});
|
||||
processor.select('rect.processor-icon-container').style('fill', null);
|
||||
processor.select('rect.border').style('stroke', null);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -18,6 +18,7 @@
|
|||
import { createAction, props } from '@ngrx/store';
|
||||
import {
|
||||
CenterComponentRequest,
|
||||
ChangeColorRequest,
|
||||
ChangeVersionDialogRequest,
|
||||
ComponentEntity,
|
||||
ConfirmStopVersionControlRequest,
|
||||
|
@ -863,3 +864,8 @@ export const openChangeProcessorVersionDialog = createAction(
|
|||
`${CANVAS_PREFIX} Open Change Processor Version Dialog`,
|
||||
props<{ request: FetchComponentVersionsRequest }>()
|
||||
);
|
||||
|
||||
export const openChangeColorDialog = createAction(
|
||||
`${CANVAS_PREFIX} Open Change Color Dialog`,
|
||||
props<{ request: ChangeColorRequest[] }>()
|
||||
);
|
||||
|
|
|
@ -135,6 +135,7 @@ import { EditLabel } from '../../ui/canvas/items/label/edit-label/edit-label.com
|
|||
import { ErrorHelper } from '../../../../service/error-helper.service';
|
||||
import { selectConnectedStateChanged } from '../../../../state/cluster-summary/cluster-summary.selectors';
|
||||
import { resetConnectedStateChanged } from '../../../../state/cluster-summary/cluster-summary.actions';
|
||||
import { ChangeColorDialog } from '../../ui/canvas/change-color-dialog/change-color-dialog.component';
|
||||
|
||||
@Injectable()
|
||||
export class FlowEffects {
|
||||
|
@ -3955,4 +3956,75 @@ export class FlowEffects {
|
|||
),
|
||||
{ dispatch: false }
|
||||
);
|
||||
|
||||
changeColor$ = createEffect(
|
||||
() =>
|
||||
this.actions$.pipe(
|
||||
ofType(FlowActions.openChangeColorDialog),
|
||||
map((action) => action.request),
|
||||
tap((request) => {
|
||||
const dialogRef = this.dialog.open(ChangeColorDialog, {
|
||||
...SMALL_DIALOG,
|
||||
data: request
|
||||
});
|
||||
|
||||
dialogRef.componentInstance.changeColor.pipe(take(1)).subscribe((requests) => {
|
||||
requests.forEach((request) => {
|
||||
const style = { ...request.style } || {};
|
||||
if (request.type === ComponentType.Processor) {
|
||||
if (request.color) {
|
||||
style['background-color'] = request.color;
|
||||
} else {
|
||||
// for processors, removing the background-color from the style map effectively unsets it
|
||||
delete style['background-color'];
|
||||
}
|
||||
this.store.dispatch(
|
||||
FlowActions.updateProcessor({
|
||||
request: {
|
||||
id: request.id,
|
||||
type: ComponentType.Processor,
|
||||
errorStrategy: 'snackbar',
|
||||
uri: request.uri,
|
||||
payload: {
|
||||
revision: request.revision,
|
||||
component: {
|
||||
id: request.id,
|
||||
style
|
||||
}
|
||||
}
|
||||
}
|
||||
})
|
||||
);
|
||||
} else if (request.type === ComponentType.Label) {
|
||||
if (request.color) {
|
||||
style['background-color'] = request.color;
|
||||
} else {
|
||||
// for labels, removing the setting the background-color style effectively unsets it
|
||||
style['background-color'] = null;
|
||||
}
|
||||
this.store.dispatch(
|
||||
FlowActions.updateComponent({
|
||||
request: {
|
||||
id: request.id,
|
||||
type: ComponentType.Label,
|
||||
errorStrategy: 'snackbar',
|
||||
uri: request.uri,
|
||||
payload: {
|
||||
revision: request.revision,
|
||||
component: {
|
||||
id: request.id,
|
||||
style
|
||||
}
|
||||
}
|
||||
}
|
||||
})
|
||||
);
|
||||
}
|
||||
});
|
||||
dialogRef.close();
|
||||
});
|
||||
})
|
||||
),
|
||||
{ dispatch: false }
|
||||
);
|
||||
}
|
||||
|
|
|
@ -854,3 +854,12 @@ export interface MoveToFrontRequest {
|
|||
revision: Revision;
|
||||
zIndex: number;
|
||||
}
|
||||
|
||||
export interface ChangeColorRequest {
|
||||
id: string;
|
||||
uri: string;
|
||||
type: ComponentType;
|
||||
color: string | null;
|
||||
revision: Revision;
|
||||
style: any | null;
|
||||
}
|
||||
|
|
|
@ -0,0 +1,66 @@
|
|||
/*!
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The ASF licenses this file to You under the Apache License, Version 2.0
|
||||
* (the "License"); you may not use this file except in compliance with
|
||||
* the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
@use 'sass:map';
|
||||
@use '@angular/material' as mat;
|
||||
|
||||
@mixin generate-theme($nifi-theme) {
|
||||
// Get the color config from the theme.
|
||||
$nifi-theme-color-config: mat.get-color-config($nifi-theme);
|
||||
|
||||
$nifi-theme-surface-palette: map.get($nifi-theme-color-config, 'primary');
|
||||
|
||||
$is-dark: map-get($nifi-theme-color-config, is-dark);
|
||||
$nifi-theme-surface-palette-lighter: mat.get-color-from-palette($nifi-theme-surface-palette, lighter);
|
||||
$nifi-theme-surface-palette-darker: mat.get-color-from-palette($nifi-theme-surface-palette, darker);
|
||||
|
||||
$nifi-theme-surface-palette-darker-contrast: mat.get-color-from-palette(
|
||||
$nifi-theme-surface-palette,
|
||||
darker-contrast
|
||||
);
|
||||
$nifi-theme-surface-palette-lighter-contrast: mat.get-color-from-palette(
|
||||
$nifi-theme-surface-palette,
|
||||
lighter-contrast
|
||||
);
|
||||
|
||||
$alternate-surface: if(
|
||||
$is-dark,
|
||||
rgba($nifi-theme-surface-palette-darker-contrast, 0.28),
|
||||
rgba($nifi-theme-surface-palette-lighter-contrast, 0.2)
|
||||
);
|
||||
|
||||
.preview {
|
||||
.processor {
|
||||
background-color: if($is-dark, $nifi-theme-surface-palette-darker, $nifi-theme-surface-palette-lighter);
|
||||
}
|
||||
|
||||
.odd {
|
||||
background-color: rgba(
|
||||
if($is-dark, $nifi-theme-surface-palette-lighter, $nifi-theme-surface-palette-darker),
|
||||
0.025
|
||||
);
|
||||
}
|
||||
|
||||
.even {
|
||||
background-color: if($is-dark, $nifi-theme-surface-palette-darker, $nifi-theme-surface-palette-lighter);
|
||||
}
|
||||
|
||||
.row-border {
|
||||
border-top: 1px solid $alternate-surface;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -0,0 +1,65 @@
|
|||
<!--
|
||||
~ Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
~ contributor license agreements. See the NOTICE file distributed with
|
||||
~ this work for additional information regarding copyright ownership.
|
||||
~ The ASF licenses this file to You under the Apache License, Version 2.0
|
||||
~ (the "License"); you may not use this file except in compliance with
|
||||
~ the License. You may obtain a copy of the License at
|
||||
~
|
||||
~ http://www.apache.org/licenses/LICENSE-2.0
|
||||
~
|
||||
~ Unless required by applicable law or agreed to in writing, software
|
||||
~ distributed under the License is distributed on an "AS IS" BASIS,
|
||||
~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
~ See the License for the specific language governing permissions and
|
||||
~ limitations under the License.
|
||||
-->
|
||||
|
||||
<h2 mat-dialog-title>Change Color</h2>
|
||||
<form [formGroup]="changeColorForm">
|
||||
<mat-dialog-content>
|
||||
<div class="flex flex-col">
|
||||
<mat-form-field>
|
||||
<mat-label>Color</mat-label>
|
||||
<input matInput type="color" formControlName="color" (change)="colorChanged()" />
|
||||
</mat-form-field>
|
||||
<mat-checkbox color="primary" [checked]="noColor" formControlName="noColor" (change)="noColorChanged()"
|
||||
>Use default color</mat-checkbox
|
||||
>
|
||||
</div>
|
||||
<div class="pt-4 preview">
|
||||
<div class="value">Preview</div>
|
||||
@if (type === ComponentType.Processor) {
|
||||
<div class="processor border drop-shadow-lg" [style.border-color]="color">
|
||||
<div class="flex flex-col">
|
||||
<div class="flex gap-x-2 items-center">
|
||||
<div class="logo flex flex-col items-center" [style.background-color]="color">
|
||||
<i
|
||||
class="icon accent-color icon-processor p-2"
|
||||
[style.color]="contrastColor"></i>
|
||||
</div>
|
||||
<div class="flex flex-col flex-1">
|
||||
<div class="context-name w-full">Processor Name</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="odd h-4"></div>
|
||||
<div class="row-border even h-4"></div>
|
||||
<div class="row-border odd h-4"></div>
|
||||
<div class="row-border even h-4"></div>
|
||||
</div>
|
||||
} @else if (type === ComponentType.Label) {
|
||||
<div
|
||||
class="label border h-36 p-2 font-bold"
|
||||
[style.background-color]="color"
|
||||
[style.color]="contrastColor">
|
||||
Label Value
|
||||
</div>
|
||||
}
|
||||
</div>
|
||||
</mat-dialog-content>
|
||||
<mat-dialog-actions align="end">
|
||||
<button mat-button mat-dialog-close>Cancel</button>
|
||||
<button mat-button [disabled]="changeColorForm.invalid" (click)="applyClicked()" color="primary">Apply</button>
|
||||
</mat-dialog-actions>
|
||||
</form>
|
|
@ -0,0 +1,25 @@
|
|||
/*!
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The ASF licenses this file to You under the Apache License, Version 2.0
|
||||
* (the "License"); you may not use this file except in compliance with
|
||||
* the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
.preview {
|
||||
.processor {
|
||||
.logo {
|
||||
.icon {
|
||||
font-size: 32px;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
|
@ -0,0 +1,52 @@
|
|||
/*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The ASF licenses this file to You under the Apache License, Version 2.0
|
||||
* (the "License"); you may not use this file except in compliance with
|
||||
* the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
import { ComponentFixture, TestBed } from '@angular/core/testing';
|
||||
import { ChangeColorDialog } from './change-color-dialog.component';
|
||||
import { MAT_DIALOG_DATA, MatDialogRef } from '@angular/material/dialog';
|
||||
import { provideMockStore } from '@ngrx/store/testing';
|
||||
import { initialState } from '../../../state/flow/flow.reducer';
|
||||
import { NoopAnimationsModule } from '@angular/platform-browser/animations';
|
||||
|
||||
describe('ChangeColorDialog', () => {
|
||||
let component: ChangeColorDialog;
|
||||
let fixture: ComponentFixture<ChangeColorDialog>;
|
||||
|
||||
beforeEach(async () => {
|
||||
await TestBed.configureTestingModule({
|
||||
imports: [ChangeColorDialog, NoopAnimationsModule],
|
||||
providers: [
|
||||
{
|
||||
provide: MAT_DIALOG_DATA,
|
||||
useValue: {
|
||||
request: []
|
||||
}
|
||||
},
|
||||
{ provide: MatDialogRef, useValue: null },
|
||||
provideMockStore({ initialState })
|
||||
]
|
||||
}).compileComponents();
|
||||
|
||||
fixture = TestBed.createComponent(ChangeColorDialog);
|
||||
component = fixture.componentInstance;
|
||||
fixture.detectChanges();
|
||||
});
|
||||
|
||||
it('should create', () => {
|
||||
expect(component).toBeTruthy();
|
||||
});
|
||||
});
|
|
@ -0,0 +1,156 @@
|
|||
/*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The ASF licenses this file to You under the Apache License, Version 2.0
|
||||
* (the "License"); you may not use this file except in compliance with
|
||||
* the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
import { Component, EventEmitter, Inject, Output } from '@angular/core';
|
||||
import { CommonModule } from '@angular/common';
|
||||
import {
|
||||
MAT_DIALOG_DATA,
|
||||
MatDialogActions,
|
||||
MatDialogClose,
|
||||
MatDialogContent,
|
||||
MatDialogTitle
|
||||
} from '@angular/material/dialog';
|
||||
import { FormBuilder, FormGroup, ReactiveFormsModule } from '@angular/forms';
|
||||
import { MatButton } from '@angular/material/button';
|
||||
import { NifiSpinnerDirective } from '../../../../../ui/common/spinner/nifi-spinner.directive';
|
||||
import { ChangeColorRequest } from '../../../state/flow';
|
||||
import { MatFormField, MatLabel } from '@angular/material/form-field';
|
||||
import { MatInput } from '@angular/material/input';
|
||||
import { ComponentContext } from '../../../../../ui/common/component-context/component-context.component';
|
||||
import { ComponentType } from '../../../../../state/shared';
|
||||
import { CloseOnEscapeDialog } from '../../../../../ui/common/close-on-escape-dialog/close-on-escape-dialog.component';
|
||||
import { ComponentTypeNamePipe } from '../../../../../pipes/component-type-name.pipe';
|
||||
import { CanvasUtils } from '../../../service/canvas-utils.service';
|
||||
import { NiFiCommon } from '../../../../../service/nifi-common.service';
|
||||
import { MatCheckbox } from '@angular/material/checkbox';
|
||||
|
||||
@Component({
|
||||
selector: 'change-component-dialog',
|
||||
standalone: true,
|
||||
imports: [
|
||||
CommonModule,
|
||||
MatDialogTitle,
|
||||
ReactiveFormsModule,
|
||||
MatDialogContent,
|
||||
MatButton,
|
||||
MatDialogActions,
|
||||
MatDialogClose,
|
||||
NifiSpinnerDirective,
|
||||
MatFormField,
|
||||
MatLabel,
|
||||
MatInput,
|
||||
ComponentContext,
|
||||
ComponentTypeNamePipe,
|
||||
MatCheckbox
|
||||
],
|
||||
templateUrl: './change-color-dialog.component.html',
|
||||
styleUrl: './change-color-dialog.component.scss'
|
||||
})
|
||||
export class ChangeColorDialog extends CloseOnEscapeDialog {
|
||||
color: string | null = null;
|
||||
noColor: boolean = true;
|
||||
contrastColor: string | null = null;
|
||||
type: ComponentType | null = null;
|
||||
changeColorForm: FormGroup;
|
||||
private _data: ChangeColorRequest[] = [];
|
||||
private DEFAULT_LABEL_COLOR = '#fff7d7';
|
||||
|
||||
@Output() changeColor = new EventEmitter<ChangeColorRequest[]>();
|
||||
|
||||
constructor(
|
||||
@Inject(MAT_DIALOG_DATA) private data: ChangeColorRequest[],
|
||||
private canvasUtils: CanvasUtils,
|
||||
private nifiCommon: NiFiCommon,
|
||||
private formBuilder: FormBuilder
|
||||
) {
|
||||
super();
|
||||
this._data = data;
|
||||
let isDefaultColor = true;
|
||||
|
||||
if (data.length > 0) {
|
||||
this.color = data[0].color;
|
||||
if (this.color !== null) {
|
||||
const hex = this.nifiCommon.substringAfterLast(this.color, '#');
|
||||
this.contrastColor = this.canvasUtils.determineContrastColor(hex);
|
||||
this.noColor = false;
|
||||
isDefaultColor = false;
|
||||
}
|
||||
this.type = data[0].type;
|
||||
if (this.type === ComponentType.Label && this.color === null) {
|
||||
this.color = this.DEFAULT_LABEL_COLOR;
|
||||
const hex = this.nifiCommon.substringAfterLast(this.color, '#');
|
||||
this.contrastColor = this.canvasUtils.determineContrastColor(hex);
|
||||
isDefaultColor = true;
|
||||
}
|
||||
}
|
||||
|
||||
this.changeColorForm = formBuilder.group({
|
||||
color: [this.color],
|
||||
noColor: [isDefaultColor]
|
||||
});
|
||||
}
|
||||
|
||||
colorChanged(): void {
|
||||
this.color = this.changeColorForm.get('color')?.value;
|
||||
if (this.color !== null) {
|
||||
const hex = this.nifiCommon.substringAfterLast(this.color, '#');
|
||||
this.contrastColor = this.canvasUtils.determineContrastColor(hex);
|
||||
this.noColor = false;
|
||||
} else {
|
||||
this.contrastColor = null;
|
||||
}
|
||||
}
|
||||
|
||||
noColorChanged(): void {
|
||||
const noColorChecked = this.changeColorForm.get('noColor')?.value;
|
||||
if (noColorChecked) {
|
||||
this.noColor = true;
|
||||
if (this.type === ComponentType.Label) {
|
||||
this.color = this.DEFAULT_LABEL_COLOR;
|
||||
const hex = this.nifiCommon.substringAfterLast(this.color, '#');
|
||||
this.contrastColor = this.canvasUtils.determineContrastColor(hex);
|
||||
} else {
|
||||
this.color = null;
|
||||
this.contrastColor = null;
|
||||
}
|
||||
} else {
|
||||
this.noColor = false;
|
||||
this.color = this.changeColorForm.get('color')?.value;
|
||||
if (this.color === null) {
|
||||
if (this.type === ComponentType.Label) {
|
||||
this.color = this.DEFAULT_LABEL_COLOR;
|
||||
} else {
|
||||
this.color = '#000000'; // default for the color picker
|
||||
}
|
||||
}
|
||||
const hex = this.nifiCommon.substringAfterLast(this.color, '#');
|
||||
this.contrastColor = this.canvasUtils.determineContrastColor(hex);
|
||||
}
|
||||
}
|
||||
|
||||
applyClicked() {
|
||||
const result: ChangeColorRequest[] = this._data.map((changeColorRequest) => {
|
||||
return {
|
||||
...changeColorRequest,
|
||||
color: this.noColor ? null : this.color
|
||||
};
|
||||
});
|
||||
this.changeColor.next(result);
|
||||
}
|
||||
|
||||
protected readonly ComponentType = ComponentType;
|
||||
}
|
|
@ -119,16 +119,15 @@
|
|||
(click)="group(selection)">
|
||||
<i class="ml-1 icon icon-group"></i>
|
||||
</button>
|
||||
<!-- TODO - Add support for coloring processors and labels -->
|
||||
<!-- <button-->
|
||||
<!-- mat-icon-button-->
|
||||
<!-- color="primary"-->
|
||||
<!-- class="mr-2"-->
|
||||
<!-- type="button"-->
|
||||
<!-- [disabled]="!canColor(selection)"-->
|
||||
<!-- (click)="color(selection)">-->
|
||||
<!-- <i class="fa fa-paint-brush"></i>-->
|
||||
<!-- </button>-->
|
||||
<button
|
||||
mat-icon-button
|
||||
color="primary"
|
||||
class="mr-2"
|
||||
type="button"
|
||||
[disabled]="!canColor(selection)"
|
||||
(click)="color(selection)">
|
||||
<i class="fa fa-paint-brush"></i>
|
||||
</button>
|
||||
<button
|
||||
mat-icon-button
|
||||
color="primary"
|
||||
|
|
|
@ -254,12 +254,11 @@ export class OperationControl {
|
|||
}
|
||||
|
||||
canColor(selection: d3.Selection<any, any, any, any>): boolean {
|
||||
// TODO
|
||||
return false;
|
||||
return this.canvasActionsService.getConditionFunction('changeColor')(selection);
|
||||
}
|
||||
|
||||
color(selection: d3.Selection<any, any, any, any>): void {
|
||||
// TODO
|
||||
this.canvasActionsService.getActionFunction('changeColor')(selection);
|
||||
}
|
||||
|
||||
canDelete(selection: d3.Selection<any, any, any, any>): boolean {
|
||||
|
|
|
@ -22,7 +22,7 @@ import { MAT_DIALOG_DATA } from '@angular/material/dialog';
|
|||
import { ComponentType } from '../../../../../../../state/shared';
|
||||
import { provideMockStore } from '@ngrx/store/testing';
|
||||
import { initialState } from '../../../../../state/flow/flow.reducer';
|
||||
import { BrowserAnimationsModule } from '@angular/platform-browser/animations';
|
||||
import { NoopAnimationsModule } from '@angular/platform-browser/animations';
|
||||
import { CreateComponentRequest } from '../../../../../state/flow';
|
||||
|
||||
describe('CreateRemoteProcessGroup', () => {
|
||||
|
@ -43,7 +43,7 @@ describe('CreateRemoteProcessGroup', () => {
|
|||
|
||||
beforeEach(() => {
|
||||
TestBed.configureTestingModule({
|
||||
imports: [CreateRemoteProcessGroup, BrowserAnimationsModule],
|
||||
imports: [CreateRemoteProcessGroup, NoopAnimationsModule],
|
||||
providers: [{ provide: MAT_DIALOG_DATA, useValue: data }, provideMockStore({ initialState })]
|
||||
});
|
||||
fixture = TestBed.createComponent(CreateRemoteProcessGroup);
|
||||
|
|
|
@ -19,7 +19,7 @@ import { ComponentFixture, TestBed } from '@angular/core/testing';
|
|||
|
||||
import { EditRemoteProcessGroup } from './edit-remote-process-group.component';
|
||||
import { MAT_DIALOG_DATA, MatDialogRef } from '@angular/material/dialog';
|
||||
import { BrowserAnimationsModule } from '@angular/platform-browser/animations';
|
||||
import { NoopAnimationsModule } from '@angular/platform-browser/animations';
|
||||
import { ComponentType } from '../../../../../../../state/shared';
|
||||
import { provideMockStore } from '@ngrx/store/testing';
|
||||
import { initialState } from '../../../../../state/flow/flow.reducer';
|
||||
|
@ -71,7 +71,7 @@ describe('EditRemoteProcessGroup', () => {
|
|||
|
||||
beforeEach(() => {
|
||||
TestBed.configureTestingModule({
|
||||
imports: [EditRemoteProcessGroup, BrowserAnimationsModule],
|
||||
imports: [EditRemoteProcessGroup, NoopAnimationsModule],
|
||||
providers: [
|
||||
{
|
||||
provide: MAT_DIALOG_DATA,
|
||||
|
|
|
@ -40,6 +40,7 @@
|
|||
@use 'app/ui/common/status-history/status-history.component-theme' as status-history;
|
||||
@use 'app/ui/common/tooltips/property-hint-tip/property-hint-tip.component-theme' as property-hint-tip;
|
||||
@use 'app/pages/summary/ui/processor-status-listing/processor-status-table/processor-status-table.component-theme' as processor-status-table;
|
||||
@use 'app/pages/flow-designer/ui/canvas/change-color-dialog/change-color-dialog.component-theme' as change-color-dialog;
|
||||
|
||||
// Plus imports for other components in your app.
|
||||
@use 'assets/fonts/flowfont/flowfont.css';
|
||||
|
@ -91,6 +92,7 @@
|
|||
@include status-history.generate-theme($nifi-theme-light);
|
||||
@include property-hint-tip.generate-theme($material-theme-light, $nifi-theme-light);
|
||||
@include processor-status-table.generate-theme($nifi-theme-light);
|
||||
@include change-color-dialog.generate-theme($nifi-theme-light);
|
||||
|
||||
.dark-theme {
|
||||
// Include the dark theme color styles.
|
||||
|
@ -119,4 +121,5 @@
|
|||
@include status-history.generate-theme($nifi-theme-dark);
|
||||
@include property-hint-tip.generate-theme($material-theme-dark, $nifi-theme-dark);
|
||||
@include processor-status-table.generate-theme($nifi-theme-dark);
|
||||
@include change-color-dialog.generate-theme($nifi-theme-dark);
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue