Moving away from Azure Devops #1
4 changed files with 65 additions and 9 deletions
|
|
@ -9,6 +9,7 @@ import { TeamRenderer } from './features/team/TeamRenderer';
|
|||
import { RendererRegistry } from './core/RendererRegistry';
|
||||
import { CalendarOrchestrator } from './core/CalendarOrchestrator';
|
||||
import { TimeAxisRenderer } from './features/timeaxis/TimeAxisRenderer';
|
||||
import { ScrollManager } from './core/ScrollManager';
|
||||
import { MockTeamStore, MockResourceStore } from './demo/MockStores';
|
||||
import { DemoApp } from './demo/DemoApp';
|
||||
|
||||
|
|
@ -45,6 +46,7 @@ export function createV2Container(): Container {
|
|||
// CalendarOrchestrator modtager IGroupingStore[] automatisk (array injection)
|
||||
builder.registerType(CalendarOrchestrator).as<CalendarOrchestrator>();
|
||||
builder.registerType(TimeAxisRenderer).as<TimeAxisRenderer>();
|
||||
builder.registerType(ScrollManager).as<ScrollManager>();
|
||||
|
||||
// Demo app
|
||||
builder.registerType(DemoApp).as<DemoApp>();
|
||||
|
|
|
|||
23
src/v2/core/ScrollManager.ts
Normal file
23
src/v2/core/ScrollManager.ts
Normal file
|
|
@ -0,0 +1,23 @@
|
|||
export class ScrollManager {
|
||||
private scrollableContent!: HTMLElement;
|
||||
private timeAxisContent!: HTMLElement;
|
||||
private calendarHeader!: HTMLElement;
|
||||
|
||||
init(container: HTMLElement): void {
|
||||
this.scrollableContent = container.querySelector('swp-scrollable-content')!;
|
||||
this.timeAxisContent = container.querySelector('swp-time-axis-content')!;
|
||||
this.calendarHeader = container.querySelector('swp-calendar-header')!;
|
||||
|
||||
this.scrollableContent.addEventListener('scroll', () => this.onScroll());
|
||||
}
|
||||
|
||||
private onScroll(): void {
|
||||
const { scrollTop, scrollLeft } = this.scrollableContent;
|
||||
|
||||
// Synkroniser time-axis vertikalt
|
||||
this.timeAxisContent.style.transform = `translateY(-${scrollTop}px)`;
|
||||
|
||||
// Synkroniser header horisontalt
|
||||
this.calendarHeader.style.transform = `translateX(-${scrollLeft}px)`;
|
||||
}
|
||||
}
|
||||
|
|
@ -2,6 +2,7 @@ import { CalendarOrchestrator } from '../core/CalendarOrchestrator';
|
|||
import { TimeAxisRenderer } from '../features/timeaxis/TimeAxisRenderer';
|
||||
import { NavigationAnimator } from '../core/NavigationAnimator';
|
||||
import { DateService } from '../core/DateService';
|
||||
import { ScrollManager } from '../core/ScrollManager';
|
||||
import { ViewConfig } from '../core/ViewConfig';
|
||||
|
||||
export class DemoApp {
|
||||
|
|
@ -13,7 +14,8 @@ export class DemoApp {
|
|||
constructor(
|
||||
private orchestrator: CalendarOrchestrator,
|
||||
private timeAxisRenderer: TimeAxisRenderer,
|
||||
private dateService: DateService
|
||||
private dateService: DateService,
|
||||
private scrollManager: ScrollManager
|
||||
) {}
|
||||
|
||||
init(): void {
|
||||
|
|
@ -49,6 +51,9 @@ export class DemoApp {
|
|||
// Render time axis
|
||||
this.timeAxisRenderer.render(document.getElementById('time-axis') as HTMLElement);
|
||||
|
||||
// Init scroll synkronisering
|
||||
this.scrollManager.init(this.container);
|
||||
|
||||
// Setup event handlers
|
||||
this.setupNavigation();
|
||||
this.setupViewSwitchers();
|
||||
|
|
|
|||
|
|
@ -2,6 +2,8 @@
|
|||
--hour-height: 60px;
|
||||
--time-axis-width: 60px;
|
||||
--grid-columns: 5;
|
||||
--day-start-hour: 0;
|
||||
--day-end-hour: 24;
|
||||
--color-border: #e0e0e0;
|
||||
--color-surface: #fff;
|
||||
--color-text-secondary: #666;
|
||||
|
|
@ -68,6 +70,7 @@ swp-calendar-container {
|
|||
grid-template-columns: var(--time-axis-width) 1fr;
|
||||
grid-template-rows: auto 1fr;
|
||||
overflow: hidden;
|
||||
height: 100%;
|
||||
}
|
||||
|
||||
/* Time axis */
|
||||
|
|
@ -78,6 +81,7 @@ swp-time-axis {
|
|||
grid-template-rows: subgrid;
|
||||
border-right: 1px solid var(--color-border);
|
||||
background: var(--color-surface);
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
swp-header-spacer {
|
||||
|
|
@ -85,8 +89,8 @@ swp-header-spacer {
|
|||
}
|
||||
|
||||
swp-time-axis-content {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
display: grid;
|
||||
grid-auto-rows: var(--hour-height);
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
|
|
@ -108,19 +112,31 @@ swp-grid-container {
|
|||
}
|
||||
|
||||
/* Viewport/Track for slide animation */
|
||||
swp-header-viewport,
|
||||
swp-content-viewport {
|
||||
swp-header-viewport {
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
swp-header-track,
|
||||
swp-content-track {
|
||||
swp-content-viewport {
|
||||
overflow: hidden;
|
||||
min-height: 0; /* Tillader at krympe i grid */
|
||||
}
|
||||
|
||||
swp-header-track {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
swp-header-track > swp-calendar-header,
|
||||
swp-content-track {
|
||||
display: flex;
|
||||
height: 100%;
|
||||
}
|
||||
|
||||
swp-header-track > swp-calendar-header {
|
||||
flex: 0 0 100%;
|
||||
}
|
||||
|
||||
swp-content-track > swp-scrollable-content {
|
||||
flex: 0 0 100%;
|
||||
height: 100%;
|
||||
}
|
||||
|
||||
/* Header */
|
||||
|
|
@ -129,6 +145,16 @@ swp-calendar-header {
|
|||
grid-template-columns: repeat(var(--grid-columns), 1fr);
|
||||
grid-auto-rows: auto;
|
||||
background: var(--color-surface);
|
||||
overflow-y: scroll;
|
||||
overflow-x: hidden;
|
||||
}
|
||||
|
||||
swp-calendar-header::-webkit-scrollbar {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
swp-calendar-header::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
swp-calendar-header[data-levels="date"] > swp-day-header { grid-row: 1; }
|
||||
|
|
@ -182,7 +208,7 @@ swp-scrollable-content {
|
|||
swp-time-grid {
|
||||
display: block;
|
||||
position: relative;
|
||||
min-height: calc(15 * var(--hour-height));
|
||||
min-height: calc((var(--day-end-hour) - var(--day-start-hour)) * var(--hour-height));
|
||||
}
|
||||
|
||||
swp-grid-lines {
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue