main
Dmitry Kalinin 6 years ago
parent 23a658f2c0
commit 5fc65c8e73

@ -399,11 +399,8 @@ export class CanvasViewImpl implements CanvasView, Listener {
this.svgTexts[state.clientID].remove(); this.svgTexts[state.clientID].remove();
} }
const shape = this.svgShapes[state.clientID]; this.svgShapes[state.clientID].off('click.canvas');
if (shape) { this.svgShapes[state.clientID].remove();
shape.off('click.canvas');
shape.remove();
}
delete this.drawnStates[state.clientID]; delete this.drawnStates[state.clientID];
} }
@ -849,7 +846,7 @@ export class CanvasViewImpl implements CanvasView, Listener {
hidden: state.hidden, hidden: state.hidden,
lock: state.lock, lock: state.lock,
shapeType: state.shapeType, shapeType: state.shapeType,
points: Array.isArray(state.points) ? [...state.points] : [], points: [...state.points],
attributes: { ...state.attributes }, attributes: { ...state.attributes },
zOrder: state.zOrder, zOrder: state.zOrder,
pinned: state.pinned, pinned: state.pinned,
@ -894,7 +891,7 @@ export class CanvasViewImpl implements CanvasView, Listener {
this.activate(activeElement); this.activate(activeElement);
} }
if (state.points && state.points if (state.points
.some((p: number, id: number): boolean => p !== drawnState.points[id]) .some((p: number, id: number): boolean => p !== drawnState.points[id])
) { ) {
const translatedPoints: number[] = translate(state.points); const translatedPoints: number[] = translate(state.points);
@ -1023,25 +1020,23 @@ export class CanvasViewImpl implements CanvasView, Listener {
const drawnState = this.drawnStates[clientID]; const drawnState = this.drawnStates[clientID];
const shape = this.svgShapes[clientID]; const shape = this.svgShapes[clientID];
if (shape) { shape.removeClass('cvat_canvas_shape_activated');
shape.removeClass('cvat_canvas_shape_activated');
if (!drawnState.pinned) {
(shape as any).off('dragstart');
(shape as any).off('dragend');
(shape as any).draggable(false);
}
if (drawnState.shapeType !== 'points') { if (!drawnState.pinned) {
this.selectize(false, shape); (shape as any).off('dragstart');
} (shape as any).off('dragend');
(shape as any).draggable(false);
}
(shape as any).off('resizestart'); if (drawnState.shapeType !== 'points') {
(shape as any).off('resizing'); this.selectize(false, shape);
(shape as any).off('resizedone');
(shape as any).resize(false);
} }
(shape as any).off('resizestart');
(shape as any).off('resizing');
(shape as any).off('resizedone');
(shape as any).resize(false);
// TODO: Hide text only if it is hidden by settings // TODO: Hide text only if it is hidden by settings
const text = this.svgTexts[clientID]; const text = this.svgTexts[clientID];
if (text) { if (text) {
@ -1090,10 +1085,6 @@ export class CanvasViewImpl implements CanvasView, Listener {
this.activeElement = { ...activeElement }; this.activeElement = { ...activeElement };
const shape = this.svgShapes[clientID]; const shape = this.svgShapes[clientID];
if (!shape) {
return;
}
let text = this.svgTexts[clientID]; let text = this.svgTexts[clientID];
if (!text) { if (!text) {
text = this.addText(state); text = this.addText(state);

@ -802,7 +802,9 @@
let minimumState = null; let minimumState = null;
for (const state of objectStates) { for (const state of objectStates) {
checkObjectType('object state', state, null, ObjectState); checkObjectType('object state', state, null, ObjectState);
if (state.outside || state.hidden) continue; if (state.outside || state.hidden || state.objectType === ObjectType.TAG) {
continue;
}
const object = this.objects[state.clientID]; const object = this.objects[state.clientID];
if (typeof (object) === 'undefined') { if (typeof (object) === 'undefined') {
@ -810,13 +812,11 @@
'The object has not been saved yet. Call annotations.put([state]) before', 'The object has not been saved yet. Call annotations.put([state]) before',
); );
} }
if (!(object instanceof Tag)) { const distance = object.constructor.distance(state.points, x, y);
const distance = object.constructor.distance(state.points, x, y); if (distance !== null && (minimumDistance === null
if (distance !== null && (minimumDistance === null || distance < minimumDistance)) {
|| distance < minimumDistance)) { minimumDistance = distance;
minimumDistance = distance; minimumState = state;
minimumState = state;
}
} }
} }

@ -8,7 +8,10 @@
*/ */
const jsonpath = require('jsonpath'); const jsonpath = require('jsonpath');
const { AttributeType } = require('./enums'); const {
AttributeType,
ObjectType,
} = require('./enums');
const { ArgumentError } = require('./exceptions'); const { ArgumentError } = require('./exceptions');
@ -167,7 +170,7 @@ class AnnotationsFilter {
let ybr = Number.MIN_SAFE_INTEGER; let ybr = Number.MIN_SAFE_INTEGER;
let [width, height] = [null, null]; let [width, height] = [null, null];
if (state.objectType !== 'tag') { if (state.objectType !== ObjectType.TAG) {
state.points.forEach((coord, idx) => { state.points.forEach((coord, idx) => {
if (idx % 2) { // y if (idx % 2) { // y
ytl = Math.min(ytl, coord); ytl = Math.min(ytl, coord);

@ -84,10 +84,10 @@ export enum AnnotationActionTypes {
COPY_SHAPE = 'COPY_SHAPE', COPY_SHAPE = 'COPY_SHAPE',
PASTE_SHAPE = 'PASTE_SHAPE', PASTE_SHAPE = 'PASTE_SHAPE',
EDIT_SHAPE = 'EDIT_SHAPE', EDIT_SHAPE = 'EDIT_SHAPE',
DRAW_SHAPE = 'DRAW_SHAPE',
REPEAT_DRAW_SHAPE = 'REPEAT_DRAW_SHAPE', REPEAT_DRAW_SHAPE = 'REPEAT_DRAW_SHAPE',
SHAPE_DRAWN = 'SHAPE_DRAWN', SHAPE_DRAWN = 'SHAPE_DRAWN',
RESET_CANVAS = 'RESET_CANVAS', RESET_CANVAS = 'RESET_CANVAS',
REMEMBER_CREATED_OBJECT = 'REMEMBER_CREATED_OBJECT',
UPDATE_ANNOTATIONS_SUCCESS = 'UPDATE_ANNOTATIONS_SUCCESS', UPDATE_ANNOTATIONS_SUCCESS = 'UPDATE_ANNOTATIONS_SUCCESS',
UPDATE_ANNOTATIONS_FAILED = 'UPDATE_ANNOTATIONS_FAILED', UPDATE_ANNOTATIONS_FAILED = 'UPDATE_ANNOTATIONS_FAILED',
CREATE_ANNOTATIONS_SUCCESS = 'CREATE_ANNOTATIONS_SUCCESS', CREATE_ANNOTATIONS_SUCCESS = 'CREATE_ANNOTATIONS_SUCCESS',
@ -844,15 +844,17 @@ ThunkAction<Promise<void>, {}, {}, AnyAction> {
}; };
} }
export function drawShape( export function rememberObject(
shapeType: ShapeType,
labelID: number,
objectType: ObjectType, objectType: ObjectType,
labelID: number,
shapeType?: ShapeType,
points?: number, points?: number,
rectDrawingMethod?: RectDrawingMethod, rectDrawingMethod?: RectDrawingMethod,
): AnyAction { ): AnyAction {
let activeControl = ActiveControl.DRAW_RECTANGLE; let activeControl = ActiveControl.CURSOR;
if (shapeType === ShapeType.POLYGON) { if (shapeType === ShapeType.RECTANGLE) {
activeControl = ActiveControl.DRAW_RECTANGLE;
} else if (shapeType === ShapeType.POLYGON) {
activeControl = ActiveControl.DRAW_POLYGON; activeControl = ActiveControl.DRAW_POLYGON;
} else if (shapeType === ShapeType.POLYLINE) { } else if (shapeType === ShapeType.POLYLINE) {
activeControl = ActiveControl.DRAW_POLYLINE; activeControl = ActiveControl.DRAW_POLYLINE;
@ -861,7 +863,7 @@ export function drawShape(
} }
return { return {
type: AnnotationActionTypes.DRAW_SHAPE, type: AnnotationActionTypes.REMEMBER_CREATED_OBJECT,
payload: { payload: {
shapeType, shapeType,
labelID, labelID,
@ -1152,10 +1154,7 @@ export function searchAnnotationsAsync(
}; };
} }
export function addTagAsync( export function pasteShapeAsync(): ThunkAction<Promise<void>, {}, {}, AnyAction> {
labelID: number,
frame: number,
): ThunkAction<Promise<void>, {}, {}, AnyAction> {
return async (dispatch: ActionCreator<Dispatch>): Promise<void> => { return async (dispatch: ActionCreator<Dispatch>): Promise<void> => {
const { const {
canvas: { canvas: {
@ -1164,40 +1163,14 @@ export function addTagAsync(
job: { job: {
instance: jobInstance, instance: jobInstance,
}, },
} = getStore().getState().annotation;
dispatch({
type: AnnotationActionTypes.ADD_TAG,
payload: {
labelID,
objectType: ObjectType.TAG,
activeControl: ActiveControl.CURSOR,
},
});
canvasInstance.cancel();
const objectState = new cvat.classes.ObjectState({
objectType: ObjectType.TAG,
label: jobInstance.task.labels
.filter((label: any) => label.id === labelID)[0],
frame,
});
dispatch(createAnnotationsAsync(jobInstance, frame, [objectState]));
};
}
export function pasteShapeAsync(): ThunkAction<Promise<void>, {}, {}, AnyAction> {
return async (dispatch: ActionCreator<Dispatch>): Promise<void> => {
const initialState = getStore().getState().annotation.drawing.activeInitialState;
const {
canvas: {
instance: canvasInstance,
},
player: { player: {
frame: { frame: {
number: frameNumber, number: frameNumber,
}, },
}, },
drawing: {
activeInitialState: initialState,
},
} = getStore().getState().annotation; } = getStore().getState().annotation;
if (initialState) { if (initialState) {
@ -1221,7 +1194,13 @@ export function pasteShapeAsync(): ThunkAction<Promise<void>, {}, {}, AnyAction>
canvasInstance.cancel(); canvasInstance.cancel();
if (initialState.objectType === ObjectType.TAG) { if (initialState.objectType === ObjectType.TAG) {
dispatch(addTagAsync(initialState.label.id, frameNumber)); const objectState = new cvat.classes.ObjectState({
objectType: ObjectType.TAG,
label: initialState.label,
attributes: initialState.attributes,
frame: frameNumber,
});
dispatch(createAnnotationsAsync(jobInstance, frameNumber, [objectState]));
} else { } else {
canvasInstance.draw({ canvasInstance.draw({
enabled: true, enabled: true,
@ -1238,6 +1217,10 @@ export function repeatDrawShapeAsync(): ThunkAction<Promise<void>, {}, {}, AnyAc
canvas: { canvas: {
instance: canvasInstance, instance: canvasInstance,
}, },
job: {
labels,
instance: jobInstance,
},
player: { player: {
frame: { frame: {
number: frameNumber, number: frameNumber,
@ -1272,7 +1255,12 @@ export function repeatDrawShapeAsync(): ThunkAction<Promise<void>, {}, {}, AnyAc
canvasInstance.cancel(); canvasInstance.cancel();
if (activeObjectType === ObjectType.TAG) { if (activeObjectType === ObjectType.TAG) {
dispatch(addTagAsync(activeLabelID, frameNumber)); const objectState = new cvat.classes.ObjectState({
objectType: ObjectType.TAG,
label: labels.filter((label: any) => label.id === activeLabelID)[0],
frame: frameNumber,
});
dispatch(createAnnotationsAsync(jobInstance, frameNumber, [objectState]));
} else { } else {
canvasInstance.draw({ canvasInstance.draw({
enabled: true, enabled: true,

@ -345,7 +345,8 @@ export default class CanvasWrapperComponent extends React.PureComponent<Props> {
} = this.props; } = this.props;
if (frameData !== null) { if (frameData !== null) {
canvasInstance.setup(frameData, annotations); canvasInstance.setup(frameData, annotations
.filter((e) => e.objectType !== ObjectType.TAG));
canvasInstance.rotate(frameAngle); canvasInstance.rotate(frameAngle);
} }
} }

@ -121,7 +121,6 @@
.cvat-objects-sidebar-state-item-color { .cvat-objects-sidebar-state-item-color {
width: 7px; width: 7px;
opacity: 1; opacity: 1;
background-color: $default-object-colorpicker-item-background-color;
&:hover { &:hover {
opacity: 0.7; opacity: 0.7;

@ -13,7 +13,7 @@ import {
} from 'reducers/interfaces'; } from 'reducers/interfaces';
import { import {
drawShape, rememberObject,
} from 'actions/annotation-actions'; } from 'actions/annotation-actions';
import { Canvas, RectDrawingMethod } from 'cvat-canvas'; import { Canvas, RectDrawingMethod } from 'cvat-canvas';
import DrawShapePopoverComponent from 'components/annotation-page/standard-workspace/controls-side-bar/draw-shape-popover'; import DrawShapePopoverComponent from 'components/annotation-page/standard-workspace/controls-side-bar/draw-shape-popover';
@ -47,7 +47,7 @@ function mapDispatchToProps(dispatch: any): DispatchToProps {
points?: number, points?: number,
rectDrawingMethod?: RectDrawingMethod, rectDrawingMethod?: RectDrawingMethod,
): void { ): void {
dispatch(drawShape(shapeType, labelID, objectType, points, rectDrawingMethod)); dispatch(rememberObject(objectType, labelID, shapeType, points, rectDrawingMethod));
}, },
}; };
} }

@ -7,26 +7,38 @@ import { connect } from 'react-redux';
import { import {
CombinedState, CombinedState,
ObjectType,
} from 'reducers/interfaces'; } from 'reducers/interfaces';
import { import {
addTagAsync, createAnnotationsAsync,
rememberObject,
} from 'actions/annotation-actions'; } from 'actions/annotation-actions';
import SetupTagPopoverComponent from 'components/annotation-page/standard-workspace/controls-side-bar/setup-tag-popover'; import SetupTagPopoverComponent from 'components/annotation-page/standard-workspace/controls-side-bar/setup-tag-popover';
import { Canvas } from 'cvat-canvas';
import getCore from 'cvat-core';
const cvat = getCore();
interface DispatchToProps { interface DispatchToProps {
onAddTag(labelID: number, frame: number): void; onAnnotationCreate(sessionInstance: any, frame: number, states: any[]): void;
onRememberObject(labelID: number): void;
} }
interface StateToProps { interface StateToProps {
canvasInstance: Canvas;
jobInstance: any;
labels: any[]; labels: any[];
frame: number; frame: number;
} }
function mapDispatchToProps(dispatch: any): DispatchToProps { function mapDispatchToProps(dispatch: any): DispatchToProps {
return { return {
onAddTag(labelID: number, frame: number): void { onAnnotationCreate(sessionInstance: any, frame: number, states: any[]): void {
dispatch(addTagAsync(labelID, frame)); dispatch(createAnnotationsAsync(sessionInstance, frame, states));
},
onRememberObject(labelID: number): void {
dispatch(rememberObject(ObjectType.TAG, labelID));
}, },
}; };
} }
@ -34,7 +46,11 @@ function mapDispatchToProps(dispatch: any): DispatchToProps {
function mapStateToProps(state: CombinedState): StateToProps { function mapStateToProps(state: CombinedState): StateToProps {
const { const {
annotation: { annotation: {
canvas: {
instance: canvasInstance,
},
job: { job: {
instance: jobInstance,
labels, labels,
}, },
player: { player: {
@ -46,6 +62,8 @@ function mapStateToProps(state: CombinedState): StateToProps {
} = state; } = state;
return { return {
canvasInstance,
jobInstance,
labels, labels,
frame, frame,
}; };
@ -76,12 +94,26 @@ class DrawShapePopoverContainer extends React.PureComponent<Props, State> {
private onSetup(): void { private onSetup(): void {
const { const {
frame, frame,
onAddTag, labels,
jobInstance,
canvasInstance,
onAnnotationCreate,
onRememberObject,
} = this.props; } = this.props;
const { selectedLabelID } = this.state; const { selectedLabelID } = this.state;
onAddTag(selectedLabelID, frame); canvasInstance.cancel();
onRememberObject(selectedLabelID);
const objectState = new cvat.classes.ObjectState({
objectType: ObjectType.TAG,
label: labels.filter((label: any) => label.id === selectedLabelID)[0],
frame,
});
onAnnotationCreate(jobInstance, frame, [objectState]);
} }
public render(): JSX.Element { public render(): JSX.Element {

@ -393,7 +393,7 @@ export default (state = defaultState, action: AnyAction): AnnotationState => {
}, },
}; };
} }
case AnnotationActionTypes.DRAW_SHAPE: { case AnnotationActionTypes.REMEMBER_CREATED_OBJECT: {
const { const {
shapeType, shapeType,
labelID, labelID,
@ -437,30 +437,6 @@ export default (state = defaultState, action: AnyAction): AnnotationState => {
}, },
}; };
} }
case AnnotationActionTypes.ADD_TAG: {
const {
labelID,
objectType,
activeControl,
} = action.payload;
return {
...state,
annotations: {
...state.annotations,
activatedStateID: null,
},
canvas: {
...state.canvas,
activeControl,
},
drawing: {
...defaultState.drawing,
activeLabelID: labelID,
activeObjectType: objectType,
},
};
}
case AnnotationActionTypes.MERGE_OBJECTS: { case AnnotationActionTypes.MERGE_OBJECTS: {
const { enabled } = action.payload; const { enabled } = action.payload;
const activeControl = enabled const activeControl = enabled

Loading…
Cancel
Save