"일꾼이 일을 잘하려면 먼저 도구를 갈고 닦아야 한다." - 공자, 『논어』.
첫 장 > 프로그램 작성 > ActivityRenderer 빌드

ActivityRenderer 빌드

2024-08-05에 게시됨
검색:658

Gantt 활동 렌더러는 ScheduleJS 뷰어의 기본 렌더러입니다. 이 문서에서는 이 활동 렌더러의 구축 방법과 이 활동 렌더러의 특징이 무엇인지 논의합니다.

사용자 정의 렌더러 클래스를 구축하는 방법

렌더러 클래스를 구축하는 첫 번째 단계는 고차 프레임워크 클래스를 확장하여 속성과 메서드를 상속하는 것입니다.

우리는 시작 및 종료 시간 차원을 통해서만 작업을 표현하려고 합니다. 이를 수행하기 위한 ScheduleJS 기본 렌더러 클래스는 ActivityBarRenderer 클래스입니다.

사용자 정의 RowActivity 클래스에서 제공하는 속성과 메서드에 액세스할 수 있도록 ActivityBarRenderer 클래스에 사용자 정의 유형 인수를 제공해야 합니다. 기본 클래스 API를 사용합니다.

ScheduleJsViewerTaskActivityRenderer 클래스를 만들어 각각의 ScheduleJsViewerTaskRow에 모든 ScheduleJsViewerTaskActivity를 그려보겠습니다.

// Import the base ActivityBarRenderer class from ScheduleJS
import {ActivityBarRenderer} from "schedule";

// Import our custom Activity and Row types
import {ScheduleJsViewerTaskActivity} from "...";
import {ScheduleJsViewerTaskRow} from "...";

// Create our custom renderer by extending the ActivityBarRenderer class
export class ScheduleJsViewerTaskActivityRenderer extends ActivityBarRenderer { }

있는 그대로 렌더러는 ActivityBarRenderer의 기본 동작을 사용하여 활동을 그리도록 이미 등록되어 있습니다. 이제 맞춤설정 방법을 살펴보겠습니다.

기본 아키텍처

ScheduleJS에서 ActivityRenderer에 특정 활동을 그리기 위해 그래픽 API를 사용하여 프로그래밍 방식으로 등록하는 클래스입니다. ScheduleJsViewerTaskActivityRenderer를 구성하기 위해 해당 코드를 세 개의 섹션으로 구분합니다.

  • 속성은 특정 그리기 절차에 대한 동작을 변경할 수 있는 변수를 보유합니다.
  • 생성자를 사용하면 렌더러의 기본 상태를 정의할 수 있습니다.
  • 그리기 방법에는 캔버스에 활동을 그리는 데 필요한 모든 지침이 포함됩니다.

속성

속성은 렌더러 전체에서 재사용되는 상수입니다. 있는 그대로 이러한 속성은 렌더러 코드에서만 직접 편집됩니다. 사용자가 UI에서 직접 이러한 설정을 수정할 수 있는 특정 화면을 상상할 수 있습니다.

// Attributes

// Pixels sizings
private readonly _parentActivityTrianglesWidthPx: number = 5;
private readonly _parentActivityTrianglesHeightPx: number = 8;
private readonly _defaultLineWidthPx: number = 0.5;

// Colors palette
private readonly _parentActivityColor: string = Color.GRAY.toCssString();
private readonly _strokeColor: string = Color.BLACK.toCssString();
private readonly _defaultActivityGreen: Color = Color.rgb(28, 187, 158);
private readonly _defaultActivityBlue: Color = Color.rgb(53, 152, 214);
private readonly _onHoverFillColor: string = Color.ORANGE.toCssString();

// Opacity ratio for baseline activities
private readonly _baselineOpacityRatio: number = 0.6;

건설자

생성자는 렌더러 수명 주기 방법과 밀접하게 연결되어 있습니다. ScheduleJS 뷰어에서는 사용자가 화면을 전환할 때마다 렌더러를 인스턴스화하여 특정성을 정의하고 이 렌더러를 구현하는 모든 탭에서 코드를 재사용하기로 결정했습니다. 이는 사용자가 이 렌더러가 포함된 화면을 선택할 때마다 생성자 함수가 실행된다는 의미입니다.

// Constructor

// The renderer requires the graphics and the current tab variable
constructor(graphics: GraphicsBase,
            private _currentRibbonMenuTab: ScheduleJsViewerRibbonMenuTabsEnum) {

  // The ActivityBarRenderer class requires the graphics and a name for the renderer
  super(graphics, ScheduleJsViewerRenderingConstants.taskActivityRendererName);

  // Default fill color when hovering an activity
  this.setFillHover(Color.web(this._onHoverFillColor));

  // Default stroke color when hovering an activity
  this.setStrokeHover(Color.BLACK);

  // Default stroke color
  this.setStroke(Color.BLACK);

  // Default thickness
  this.setLineWidth(this._defaultLineWidthPx);

  // Default bar height
  this.setBarHeight(8);

  // Default fill color based on current tab 
  switch (_currentRibbonMenuTab) {
    // Change color for the WBS tab
    case ScheduleJsViewerRibbonMenuTabsEnum.WBS:
      this._parentActivityColor = ScheduleJsViewerColors.brown;
      this.setFill(this._defaultActivityBlue);
      break;
    default:
      this._parentActivityColor = Color.GRAY.toCssString();
      this.setFill(this._defaultActivityGreen);
      break;
  }

}

setFill, setStroke, setFillHover, setStrokeHover, setLineWidth 및 setBarHeight는 상속되어 ActivityBarRenderer 클래스의 기본 렌더링 특성을 변경하는 데 사용됩니다.

이 렌더러의 기본 기능은 다음과 같습니다.

  • 호버링 활동 시 맞춤 색상
  • 검은색 선 획(활동 테두리용)
  • 0.5픽셀의 획 선 두께
  • 액티비티 바 높이 8픽셀
  • 조건부 채우기 색상: WBS 탭에서 어린이는 파란색, 부모는 갈색 다른 탭의 어린이는 녹색, 부모는 회색

그림

프레임워크는 자동으로 drawActivity 메서드를 호출하여 활동을 캔버스에 렌더링합니다. 모든 매개변수는 동적으로 채워져 현재 활동 상태에 실시간으로 반응할 수 있습니다.

// Main drawing method

drawActivity(activityRef: ActivityRef,
             position: ViewPosition,
             ctx: CanvasRenderingContext2D,
             x: number,
             y: number,
             w: number,
             h: number,
             selected: boolean,    
             hover: boolean,
             highlighted: boolean,
             pressed: boolean     
            ): ActivityBounds {    // This method has to return ActivityBounds

    // True if current activity includes a comparison task
    const hasModifications = !!activityRef.getActivity().diffTask;

    // True if current row has children
    const isParent = activityRef.getRow().getChildren().length;

    // Set colors dynamically
    this._setActivityColor(activityRef, hasModifications);

    // Draw text
    this._drawActivityText(activityRef, ctx, x, y, w, h, hasModifications);

    // Run a custom method to draw parent activities or delegate to the default method
    return isParent
      ? this._drawParentActivity(activityRef, ctx, x, y, w, h, hover, hasModifications)
      : super.drawActivity(activityRef, position, ctx, x, y, w, h, selected, hover, highlighted, pressed);
  }

그림은 다음과 같이 진행됩니다:

  • ActivityRef API를 사용하여 현재 활동에 대한 정보를 가져옵니다.
  • _setActivityColor 메소드를 사용하여 동적으로 색상을 설정합니다.
  • _drawActivityText 메소드를 사용하여 활동 텍스트 그리기
  • 두 가지 방법을 사용하여 활동 자체를 그립니다. 부모를 그리는 _drawParentActivity 메서드 자식을 그리는 super.drawActivity 기본 ActivityBarRenderer 메서드

사용자 정의 활동 그리기 방법

_drawParentActivity 메소드를 이용해 자신만의 메소드를 디자인하여 액티비티를 자유롭게 그리는 방법을 자세히 살펴보겠습니다.

// Draw the parent activity

private _drawParentActivity(activityRef: ActivityRef,
                            ctx: CanvasRenderingContext2D,
                            x: number,
                            y: number,
                            w: number,
                            h: number,
                            hover: boolean,
                            hasModifications: boolean
                           ): ActivityBounds {

    // Set padding
    const topPadding = h / 3.5;
    const leftPadding = 1;

    // Set CanvasRenderingContext2D
    ctx.lineWidth = this._defaultLineWidthPx;
    if (hover) {
      ctx.fillStyle = this._onHoverFillColor;
      ctx.strokeStyle = ScheduleJsViewerColors.brown;
    } else if (hasModifications) {
      ctx.fillStyle = Color.web(this._parentActivityColor).withOpacity(this._baselineOpacityRatio).toCssString();
      ctx.strokeStyle = `rgba(0,0,0,${this._baselineOpacityRatio})`;
    } else {
      ctx.fillStyle = this._parentActivityColor;
      ctx.strokeStyle = this._strokeColor;
    }

    // Draw elements
    ScheduleJsViewerTaskActivityRenderer._drawParentActivityStartTriangle(ctx, x   leftPadding, y   topPadding, this._parentActivityTrianglesWidthPx, this._parentActivityTrianglesHeightPx);
    ScheduleJsViewerTaskActivityRenderer._drawParentActivityBody(ctx, x   leftPadding, y   topPadding, w, this._parentActivityTrianglesWidthPx, this._parentActivityTrianglesHeightPx);
    ScheduleJsViewerTaskActivityRenderer._drawParentActivityEndTriangle(ctx, x   leftPadding, y   topPadding, w, this._parentActivityTrianglesWidthPx, this._parentActivityTrianglesHeightPx);

    // Return positions to update where your activity should be responsive
    return new ActivityBounds(activityRef, x, y, w, h);
  }

여기에서는 HTMLCanvas API를 직접 사용하여 CanvasRenderingContex2D를 설정하여 그리기 전략을 정의합니다. 이 메서드에서 수행되는 유일한 프레임워크 관련 작업은 현재 상위 Activity.에 대한 새로운 ActivityBounds

를 만드는 것입니다.

프레임워크는 내부적으로 ActivityBounds를 사용하여 지도를 생성하여 화면의 모든 활동을 등록합니다. 이 지도는 HTMLCanvas API

의 성능을 활용하면서 정확한 정보를 기반으로 고급 사용자 경험을 구축할 수 있는 요소와 같은 논리를 제공함으로써 개발자를 돕습니다.

_drawParentActivityStartTriangle과 같은 그리기 요소 메서드는 CanvasRenderingContext2D API를 사용하여 픽셀 수준에서 그립니다.

// Draw the start triangle element of the parent activity

private static _drawParentActivityStartTriangle(ctx: CanvasRenderingContext2D,
                                                x: number,
                                                y: number,
                                                triangleWidth: number,
                                                triangleHeight: number): void {
    ctx.beginPath();
    ctx.moveTo(x, y);
    ctx.lineTo(x , y   triangleHeight);
    ctx.lineTo(x   triangleWidth, y);
    ctx.lineTo(x, y);
    ctx.fill();
    ctx.stroke();
    ctx.closePath();
}

최종 결과

새로운 렌더러를 등록하려면 graphic.setActivityRenderer 메소드를 사용하세요.

// Register the renderer

graphics.setActivityRenderer(ScheduleJsViewerTaskActivity, GanttLayout, new ScheduleJsViewerTaskActivityRenderer(graphics, currentRibbonMenuTab));

brand-new renderer

최종 결과의 비디오를 보려면 ActivityRenderer 구축을 참조하세요.

릴리스 선언문 이 기사는 https://dev.to/lenormor/building-an-activityrenderer-3o0?1에서 복제됩니다. 침해 내용이 있는 경우, [email protected]으로 연락하여 삭제하시기 바랍니다.
최신 튜토리얼 더>

부인 성명: 제공된 모든 리소스는 부분적으로 인터넷에서 가져온 것입니다. 귀하의 저작권이나 기타 권리 및 이익이 침해된 경우 자세한 이유를 설명하고 저작권 또는 권리 및 이익에 대한 증거를 제공한 후 이메일([email protected])로 보내주십시오. 최대한 빨리 처리해 드리겠습니다.

Copyright© 2022 湘ICP备2022001581号-3