---
title: "Angular Timeline Compare Resources Fixed at Top Example | Mobiscroll"
component: "Timeline"
framework: "Angular"
library_version: "6.1.5"
url: "https://demo.mobiscroll.com/angular/timeline/compare-resources-fixed-at-top"
---

# Compare Resources Fixed at Top - Angular Timeline demo

Use the Angular Timeline to pin up to 3 resources to a fixed comparison section at the top — compare schedules side by side while the rest scroll below. For Angular 22 and Ionic 8.

- [Live demo](https://demo.mobiscroll.com/angular/timeline/compare-resources-fixed-at-top)
- [View code on GitHub](https://github.com/acidb/mobiscroll-demos-angular/tree/main/src/demos/eventcalendar/timeline/compare-resources-fixed-at-top)
- This demo in other frameworks: [JavaScript](https://demo.mobiscroll.com/javascript/timeline/compare-resources-fixed-at-top.md), [jQuery](https://demo.mobiscroll.com/jquery/timeline/compare-resources-fixed-at-top.md), [React](https://demo.mobiscroll.com/react/timeline/compare-resources-fixed-at-top.md), [Vue](https://demo.mobiscroll.com/vue/timeline/compare-resources-fixed-at-top.md)

## Description

With the combination of the [timeline view](https://mobiscroll.com/docs/angular/eventcalendar/api#opt-view) along with fixed [`resources`](https://mobiscroll.com/docs/angular/eventcalendar/api#opt-resources) and [`resource templating`](https://mobiscroll.com/docs/angular/eventcalendar/api#template-resourceTemplate) you can create a UI for comparison.

In this example resources are people with tasks. There is a button in the resource template which on click dynamically moves the resource to/from a comparison section, located at the top of the view. Compare up to 3 resources at a time, but adjust this as you like in your own implementation.

## What this demo shows

- A desktop timeline view for comparing work assignments across multiple resources in a Monday-to-Friday work week.
- **Header navigation** The month and year label in the top left opens date navigation, while the blue previous and next arrows and the Today button on the right make it easy to move between weeks and jump back to the current day.
- **Week view** The fixed date strip shows the selected work week from Monday to Friday using the `DD DDD MMM YYYY` date format, with the current date highlighted in blue.
- **Time grid** The timeline displays working hours from 9 AM to 5 PM with hourly columns under each day.
- **Resources** The left side lists 12 resources, each with a Compare button next to the resource name.
- **Resource comparison** Clicking Compare pins that resource to the top of the resource list so the remaining resources can scroll below it for comparison.
- **Pinned resources** A pinned resource shows a Remove button, which unpins it and returns it to the scrolling resource list.
- **Comparison limit** Up to 3 resources can be pinned at the top of the timeline at the same time.
- **Current time** The current time is marked with a vertical blue line and a time label.
- **Hover behavior** Hovering over the time grid shows a time indicator that follows the cursor in 15-minute increments.
- **Event cards** Events are shown as colored cards with a colored stripe, bold event title, and exact start and end time.
- **Resource colors** Events use a consistent color per resource, so tasks belonging to the same resource share the same event color.
- **Event positioning** Events are positioned by resource, date, start time, and end time.
- **Event overlapping** Overlapping events stack within the resource row so each event remains visible, with the row height increasing as needed.
- **Event creation** New events can be created by double-clicking in the timeline or by dragging across a time range.
- **Event interaction** Events highlight on hover and show drag and resize handles for moving events or changing their duration.
- **Event selection** Clicking an event selects and highlights it.
- **Vertical scrolling** The resource area scrolls vertically so the timeline can display many resources.
- **Horizontal scrolling** The timeline supports horizontal scrolling for navigating the visible date and time grid.

## Best for

- **Field service scheduling** Assigning jobs to technicians across multiple workdays while keeping selected team members pinned for comparison.
- **Workforce planning** Comparing availability, assignments, and workload across several people or teams in the same timeline.
- **Maintenance management** Scheduling maintenance tasks across resources while reviewing fixed resources against the rest of the list.
- **Work order assignment** Placing and adjusting tasks by resource, date, start time, and end time.
- **Resource comparison** Keeping up to 3 important resources fixed at the top while scrolling through the remaining resources.
- **Multi-resource scheduling** Managing many resources and tasks at the same time in a work-week timeline.

## API used in this demo

- [`theme`](https://mobiscroll.com/docs/angular/eventcalendar/api#opt-theme) - option
- [`themeVariant`](https://mobiscroll.com/docs/angular/eventcalendar/api#opt-themeVariant) - option
- [`resources`](https://mobiscroll.com/docs/angular/eventcalendar/api#opt-resources) - option
- [`view`](https://mobiscroll.com/docs/angular/eventcalendar/api#opt-view) - option
- [`data`](https://mobiscroll.com/docs/angular/eventcalendar/api#opt-data) - option
- [`dragToMove`](https://mobiscroll.com/docs/angular/eventcalendar/api#opt-dragToMove) - option
- [`resourceTemplate`](https://mobiscroll.com/docs/angular/eventcalendar/api#template-resourceTemplate) - template

## Code

### Component

```ts
import { CommonModule } from '@angular/common';
import { Component } from '@angular/core';
import {
  MbscCalendarEvent,
  MbscEventcalendarView,
  MbscModule,
  MbscResource,
  Notifications,
  setOptions,
} from '@mobiscroll/angular';

setOptions({
  theme: 'ios',
  themeVariant: 'light'
});

@Component({
  selector: 'app-root', 
  templateUrl: './app.component.html',
  providers: [Notifications],
  standalone: true,
  imports: [CommonModule, MbscModule],
})
export class AppComponent {
  constructor(private notify: Notifications) {}

  myEvents: MbscCalendarEvent[] = [
    {
      start: '2026-10-22T09:00',
      end: '2026-10-22T12:00',
      title: 'Task 1',
      resource: 1,
    },
    {
      start: '2026-10-22T15:00',
      end: '2026-10-22T17:00',
      title: 'Task 2',
      resource: 1,
    },
    {
      start: '2026-10-21T11:00',
      end: '2026-10-21T16:00',
      title: 'Task 3',
      resource: 1,
    },
    {
      start: '2026-10-23T14:00',
      end: '2026-10-23T17:00',
      title: 'Task 4',
      resource: 1,
    },
    {
      start: '2026-10-24T09:00',
      end: '2026-10-24T14:00',
      title: 'Task 5',
      resource: 1,
    },
    {
      start: '2026-10-22T12:00',
      end: '2026-10-22T17:00',
      title: 'Task 6',
      resource: 2,
    },
    {
      start: '2026-10-23T09:00',
      end: '2026-10-23T14:00',
      title: 'Task 7',
      resource: 2,
    },
    {
      start: '2026-10-21T09:00',
      end: '2026-10-21T16:00',
      title: 'Task 8',
      resource: 2,
    },
    {
      start: '2026-10-24T09:00',
      end: '2026-10-24T11:00',
      title: 'Task 9',
      resource: 2,
    },
    {
      start: '2026-10-24T13:00',
      end: '2026-10-24T17:00',
      title: 'Task 10',
      resource: 2,
    },
    {
      start: '2026-10-22T10:00',
      end: '2026-10-22T14:00',
      title: 'Task 11',
      resource: 3,
    },
    {
      start: '2026-10-22T15:00',
      end: '2026-10-22T17:00',
      title: 'Task 12',
      resource: 3,
    },
    {
      start: '2026-10-23T09:00',
      end: '2026-10-23T13:00',
      title: 'Task 13',
      resource: 3,
    },
    {
      start: '2026-10-24T09:00',
      end: '2026-10-24T10:00',
      title: 'Task 14',
      resource: 3,
    },
    {
      start: '2026-10-24T14:00',
      end: '2026-10-24T16:00',
      title: 'Task 15',
      resource: 3,
    },
    {
      start: '2026-10-22T14:00',
      end: '2026-10-22T17:00',
      title: 'Task 16',
      resource: 4,
    },
    {
      start: '2026-10-21T09:00',
      end: '2026-10-21T14:00',
      title: 'Task 17',
      resource: 4,
    },
    {
      start: '2026-10-23T10:00',
      end: '2026-10-23T12:00',
      title: 'Task 18',
      resource: 4,
    },
    {
      start: '2026-10-23T14:00',
      end: '2026-10-23T17:00',
      title: 'Task 19',
      resource: 4,
    },
    {
      start: '2026-10-24T10:09',
      end: '2026-10-24T11:17',
      title: 'Task 20',
      resource: 4,
    },
    {
      start: '2026-10-22T12:00',
      end: '2026-10-22T15:00',
      title: 'Task 21',
      resource: 5,
    },
    {
      start: '2026-10-22T16:00',
      end: '2026-10-22T17:00',
      title: 'Task 22',
      resource: 5,
    },
    {
      start: '2026-10-21T11:00',
      end: '2026-10-21T15:00',
      title: 'Task 23',
      resource: 5,
    },
    {
      start: '2026-10-23T09:00',
      end: '2026-10-23T12:00',
      title: 'Task 24',
      resource: 5,
    },
    {
      start: '2026-10-24T11:00',
      end: '2026-10-24T16:00',
      title: 'Task 25',
      resource: 5,
    },
    {
      start: '2026-10-22T12:00',
      end: '2026-10-22T17:00',
      title: 'Task 26',
      resource: 6,
    },
    {
      start: '2026-10-21T10:00',
      end: '2026-10-21T14:00',
      title: 'Task 27',
      resource: 6,
    },
    {
      start: '2026-10-23T09:00',
      end: '2026-10-23T11:00',
      title: 'Task 28',
      resource: 6,
    },
    {
      start: '2026-10-23T14:00',
      end: '2026-10-23T15:00',
      title: 'Task 29',
      resource: 6,
    },
    {
      start: '2026-10-24T16:00',
      end: '2026-10-24T17:00',
      title: 'Task 30',
      resource: 6,
    },
    {
      start: '2026-10-21T15:00',
      end: '2026-10-21T17:00',
      title: 'Task 31',
      resource: 7,
    },
    {
      start: '2026-10-23T09:00',
      end: '2026-10-23T12:00',
      title: 'Task 32',
      resource: 7,
    },
    {
      start: '2026-10-23T13:00',
      end: '2026-10-23T17:00',
      title: 'Task 33',
      resource: 7,
    },
    {
      start: '2026-10-24T14:00',
      end: '2026-10-24T17:00',
      title: 'Task 34',
      resource: 7,
    },
    {
      start: '2026-10-22T10:00',
      end: '2026-10-22T12:00',
      title: 'Task 35',
      resource: 8,
    },
    {
      start: '2026-10-22T14:00',
      end: '2026-10-22T17:00',
      title: 'Task 36',
      resource: 8,
    },
    {
      start: '2026-10-23T10:00',
      end: '2026-10-23T14:00',
      title: 'Task 37',
      resource: 8,
    },
    {
      start: '2026-10-24T09:00',
      end: '2026-10-24T16:00',
      title: 'Task 38',
      resource: 8,
    },
    {
      start: '2026-10-22T09:00',
      end: '2026-10-22T17:00',
      title: 'Task 39',
      resource: 9,
    },
    {
      start: '2026-10-23T09:00',
      end: '2026-10-23T13:00',
      title: 'Task 40',
      resource: 9,
    },
    {
      start: '2026-10-23T14:00',
      end: '2026-10-23T17:00',
      title: 'Task 41',
      resource: 9,
    },
    {
      start: '2026-10-21T10:00',
      end: '2026-10-21T14:00',
      title: 'Task 42',
      resource: 9,
    },
    {
      start: '2026-10-22T10:00',
      end: '2026-10-22T15:00',
      title: 'Task 43',
      resource: 10,
    },
    {
      start: '2026-10-21T09:00',
      end: '2026-10-21T13:00',
      title: 'Work order #41989',
      resource: 10,
    },
    {
      start: '2026-10-23T09:00',
      end: '2026-10-23T17:00',
      title: 'Task 44',
      resource: 10,
    },
    {
      start: '2026-10-24T09:00',
      end: '2026-10-24T13:00',
      title: 'Task 45',
      resource: 10,
    },
    {
      start: '2026-10-24T14:00',
      end: '2026-10-24T17:00',
      title: 'Task 46',
      resource: 10,
    },
    {
      start: '2026-10-24T09:00',
      end: '2026-10-24T17:00',
      title: 'Task 47',
      resource: 11,
    },
    {
      start: '2026-10-21T12:00',
      end: '2026-10-21T17:00',
      title: 'Task 48',
      resource: 11,
    },
    {
      start: '2026-10-22T09:00',
      end: '2026-10-22T15:00',
      title: 'Task 49',
      resource: 12,
    },
    {
      start: '2026-10-24T11:00',
      end: '2026-10-24T17:00',
      title: 'Task 50',
      resource: 12,
    },
    {
      start: '2026-10-22T11:00',
      end: '2026-10-22T15:00',
      title: 'Task 51',
      resource: 13,
    },
    {
      start: '2026-10-23T09:00',
      end: '2026-10-23T17:00',
      title: 'Task 52',
      resource: 13,
    },
  ];

  myResources: MbscResource[] = [
    {
      id: 1,
      name: 'Emma Smith',
      color: '#c8cdcf',
    },
    {
      id: 2,
      name: 'James Brown',
      color: '#76e083',
    },
    {
      id: 3,
      name: 'Olivia Miller',
      color: '#4981d6',
    },
    {
      id: 4,
      name: 'David Johnson',
      color: '#d6d145',
    },
    {
      id: 5,
      name: 'Sarah Jones',
      color: '#e25dd2',
    },
    {
      id: 6,
      name: 'Joseph Davis',
      color: '#62ab50',
    },
    {
      id: 7,
      name: 'Sophia Williams',
      color: '#eb5b34',
    },
    {
      id: 8,
      name: 'Daniel Wilson',
      color: '#7134eb',
    },
    {
      id: 9,
      name: 'Alice Clark',
      color: '#a1eb34',
    },
    {
      id: 10,
      name: 'Robert Taylor',
      color: '#9b77d9',
    },
    {
      id: 11,
      name: 'Anthony Lopez',
      color: '#6bede7',
    },
    {
      id: 12,
      name: 'Grace Moore',
      color: '#262f80',
    },
    {
      id: 13,
      name: 'Peter Jackson',
      color: '#788026',
    },
  ];
  resources: MbscResource[] = this.myResources;
  fixedResources: MbscResource[] = [];
  fixedNr = 0;
  toggleComparison = (resource: MbscResource) => {
    const origResource = this.myResources.find((r) => r.id === resource.id);
    if (!resource.fixed) {
      this.fixedNr++;
      origResource!.fixed = true;
      this.fixedResources.push(origResource!);
      if (this.fixedNr > 2) {
        this.notify.toast({
          message: 'Comparing up to 3 schedules',
        });
      }
    } else {
      this.fixedNr--;
      origResource!.fixed = false;
      this.fixedResources = this.fixedResources.filter((r) => r.id !== resource.id);
    }
    const result = [...this.fixedResources];
    this.myResources.forEach((r) => {
      if (!r.fixed) {
        result.push(r);
      }
    });
    this.resources = result;
  };
  view: MbscEventcalendarView = {
    timeline: {
      type: 'week',
      resolutionHorizontal: 'hour',
      startTime: '09:00',
      endTime: '17:00',
      startDay: 1,
      endDay: 5,
    },
  };
}
```

### Template

```html
<mbsc-eventcalendar
  [data]="myEvents"
  [resources]="resources"
  [view]="view"
  [dragToMove]="true"
  [resourceTemplate]="resourceTmpl"
  class="md-compare"
>
  <ng-template #resourceTmpl let-resource>
    <div class="md-compare-resource mbsc-flex mbsc-align-items-center mbsc-justify-content-between">
      <div>{{resource.name}}</div>
      <mbsc-button
        *ngIf="resource.fixed || (!resource.fixed && (fixedNr <= 2))"
        (click)="toggleComparison(resource)"
        class="md-compare-button"
        [color]="resource.fixed ? 'danger' : 'success'"
        variant="outline"
      >
        {{resource.fixed ? "Remove" : "Compare"}}
      </mbsc-button>
    </div>
  </ng-template>
</mbsc-eventcalendar>
```

### CSS

```css
.md-compare-resource {
  font-size: 12px;
}

.md-compare-resource .md-compare-button {
  font-size: 10px;
  line-height: 1.5em;
}

.md-compare .mbsc-timeline-row-gutter {
  height: 6px;
}
```

## Implementation notes

- Use `type: 'week'` with `startDay: 1`/`endDay: 5`, `startTime: '09:00'`/`endTime: '17:00'`, and `resolutionHorizontal: 'hour'` for a Mon-Fri working-hours timeline.
- Set `fixed: true` on a resource object to pin its row to the top of the timeline so it stays visible while the rest of the list scrolls.
- Use `renderResource` (Angular: `resourceTemplate`, Vue: `#resource` slot) to show the resource name alongside a Compare or Remove button.
- Show a "Compare" button (success style) for unfixed resources when fewer than 3 are already pinned; show a "Remove" button (danger style) for pinned resources; hide the button entirely once the 3-resource limit is reached.
- On Compare click, set `fixed: true` on the resource, add it to the fixed list, and rebuild the resources array with fixed resources first followed by the rest - this drives both the pin behavior and the visual order in the timeline.
- On Remove click, set `fixed: false`, remove the resource from the fixed list, and rebuild the array in the same way.
- Track the number of fixed resources in state and show a `Toast` when the user pins the third resource (the maximum allowed is 3).
- Enable `dragToMove: true` so tasks can be repositioned across resources and days.

## Run it in your project

1. If not signed up yet, or don't own a license, you can [start a free trial](https://mobiscroll.com/starttrial).

2. Clone the repository:

   ```
   git clone https://github.com/acidb/mobiscroll-demos-angular.git
   ```

3. If not installed yet, install the Mobiscroll CLI from NPM:

   ```
   npm install -g @mobiscroll/cli
   ```

4. Config Mobiscroll - open a terminal window in the root directory and run:

   ```
   mobiscroll config angular
   ```

5. Install dependencies - open a terminal window in the root directory and run:

   ```
   npm install
   ```

6. Run the project:

   ```
   ng serve
   ```

On a trial, add `--trial` to the config command: `mobiscroll config angular --trial`.

Running a demo locally requires a Mobiscroll trial or a license; setup is per framework at https://mobiscroll.com/docs/angular/getting-started/installation

## Related demos

- Previous: [Monthly Timetable View](https://demo.mobiscroll.com/angular/timeline/monthly-timetable-vertical-days-horizontal-times.md) - Display a monthly timetable in the Angular Timeline — days listed vertically, hours across, with drag-to-create in a single-resource layout.
- Next: [Work Order Assignment](https://demo.mobiscroll.com/angular/timeline/assign-unassign-work-orders-fixed-top-row.md) - Assign work orders to employees on a Angular Timeline — keep unassigned orders in a fixed top row while scrolling, and drag to assign without changing time.
