Skip to content

Commit caaf96c

Browse files
committed
feat: add support for rtl
Closes #1203
1 parent 1982496 commit caaf96c

12 files changed

+494
-19
lines changed

projects/angular-calendar/src/modules/common/calendar-resize-helper.provider.ts

+16-2
Original file line numberDiff line numberDiff line change
@@ -3,10 +3,24 @@ import { isInside } from './util';
33
export class CalendarResizeHelper {
44
constructor(
55
private resizeContainerElement: HTMLElement,
6-
private minWidth?: number
6+
private minWidth: number,
7+
private rtl: boolean
78
) {}
89

9-
validateResize({ rectangle }: { rectangle: ClientRect }): boolean {
10+
validateResize({ rectangle, edges }): boolean {
11+
if (this.rtl) {
12+
// TODO - find a way of testing this, for some reason the tests always fail but it does actually work
13+
/* istanbul ignore next */
14+
if (typeof edges.left !== 'undefined') {
15+
rectangle.left -= edges.left;
16+
rectangle.right += edges.left;
17+
} else if (typeof edges.right !== 'undefined') {
18+
rectangle.left += edges.right;
19+
rectangle.right -= edges.right;
20+
}
21+
rectangle.width = rectangle.right - rectangle.left;
22+
}
23+
1024
if (
1125
this.minWidth &&
1226
Math.ceil(rectangle.width) < Math.ceil(this.minWidth)

projects/angular-calendar/src/modules/day/calendar-day-view.scss

+10
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,11 @@
66

77
.cal-events-container {
88
margin-left: 70px;
9+
10+
[dir='rtl'] & {
11+
margin-left: initial;
12+
margin-right: 70px;
13+
}
914
}
1015

1116
.cal-day-column {
@@ -15,5 +20,10 @@
1520
.cal-current-time-marker {
1621
margin-left: 70px;
1722
width: calc(100% - 70px);
23+
24+
[dir='rtl'] & {
25+
margin-left: initial;
26+
margin-right: 70px;
27+
}
1828
}
1929
}

projects/angular-calendar/src/modules/month/calendar-month-view.scss

+10
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,11 @@ $cal-month-view-vars: map-merge($cal-vars, $cal-month-view-vars);
2424

2525
.cal-day-cell:not(:last-child) {
2626
border-right-color: map-get($theme, border-color);
27+
28+
[dir='rtl'] & {
29+
border-right-color: initial;
30+
border-left-color: map-get($theme, border-color);
31+
}
2732
}
2833

2934
.cal-days .cal-cell-row {
@@ -112,6 +117,11 @@ $cal-month-view-vars: map-merge($cal-vars, $cal-month-view-vars);
112117

113118
.cal-day-cell:not(:last-child) {
114119
border-right: 1px solid;
120+
121+
[dir='rtl'] & {
122+
border-right: initial;
123+
border-left: 1px solid;
124+
}
115125
}
116126

117127
.cal-days .cal-cell-row {

projects/angular-calendar/src/modules/week/calendar-week-view.component.ts

+45-15
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,8 @@ import {
1010
LOCALE_ID,
1111
Inject,
1212
TemplateRef,
13+
ElementRef,
14+
AfterViewInit,
1315
} from '@angular/core';
1416
import { Subject, Subscription } from 'rxjs';
1517
import {
@@ -133,7 +135,14 @@ export interface CalendarWeekViewBeforeRenderEvent extends WeekView {
133135
[class.cal-ends-within-week]="!allDayEvent.endsAfterWeek"
134136
[ngClass]="allDayEvent.event?.cssClass"
135137
[style.width.%]="(100 / days.length) * allDayEvent.span"
136-
[style.marginLeft.%]="(100 / days.length) * allDayEvent.offset"
138+
[style.marginLeft.%]="
139+
rtl ? null : (100 / days.length) * allDayEvent.offset
140+
"
141+
[style.marginRight.%]="
142+
rtl
143+
? (100 / days.length) * (days.length - allDayEvent.offset) * -1
144+
: null
145+
"
137146
mwlResizable
138147
[resizeSnapGrid]="{ left: dayColumnWidth, right: dayColumnWidth }"
139148
[validateResize]="validateResize"
@@ -408,7 +417,8 @@ export interface CalendarWeekViewBeforeRenderEvent extends WeekView {
408417
</div>
409418
`,
410419
})
411-
export class CalendarWeekViewComponent implements OnChanges, OnInit, OnDestroy {
420+
export class CalendarWeekViewComponent
421+
implements OnChanges, OnInit, OnDestroy, AfterViewInit {
412422
/**
413423
* The current view date
414424
*/
@@ -676,6 +686,11 @@ export class CalendarWeekViewComponent implements OnChanges, OnInit, OnDestroy {
676686
*/
677687
lastDraggedEvent: CalendarEvent;
678688

689+
/**
690+
* @hidden
691+
*/
692+
rtl = false;
693+
679694
/**
680695
* @hidden
681696
*/
@@ -713,7 +728,8 @@ export class CalendarWeekViewComponent implements OnChanges, OnInit, OnDestroy {
713728
protected cdr: ChangeDetectorRef,
714729
protected utils: CalendarUtils,
715730
@Inject(LOCALE_ID) locale: string,
716-
protected dateAdapter: DateAdapter
731+
protected dateAdapter: DateAdapter,
732+
protected element: ElementRef<HTMLElement>
717733
) {
718734
this.locale = locale;
719735
}
@@ -794,6 +810,14 @@ export class CalendarWeekViewComponent implements OnChanges, OnInit, OnDestroy {
794810
}
795811
}
796812

813+
/**
814+
* @hidden
815+
*/
816+
ngAfterViewInit() {
817+
this.rtl = getComputedStyle(this.element.nativeElement).direction === 'rtl';
818+
this.cdr.detectChanges();
819+
}
820+
797821
/**
798822
* @hidden
799823
*/
@@ -881,12 +905,15 @@ export class CalendarWeekViewComponent implements OnChanges, OnInit, OnDestroy {
881905
allDayEvent
882906
);
883907

908+
const modifier = this.rtl ? -1 : 1;
884909
if (typeof resizeEvent.edges.left !== 'undefined') {
885-
const diff: number = Math.round(+resizeEvent.edges.left / dayWidth);
910+
const diff: number =
911+
Math.round(+resizeEvent.edges.left / dayWidth) * modifier;
886912
allDayEvent.offset = currentResize.originalOffset + diff;
887913
allDayEvent.span = currentResize.originalSpan - diff;
888914
} else if (typeof resizeEvent.edges.right !== 'undefined') {
889-
const diff: number = Math.round(+resizeEvent.edges.right / dayWidth);
915+
const diff: number =
916+
Math.round(+resizeEvent.edges.right / dayWidth) * modifier;
890917
allDayEvent.span = currentResize.originalSpan + diff;
891918
}
892919
}
@@ -1176,7 +1203,9 @@ export class CalendarWeekViewComponent implements OnChanges, OnInit, OnDestroy {
11761203
dayWidth: number,
11771204
useY: boolean
11781205
) {
1179-
const daysDragged = roundToNearest(dragEndEvent.x, dayWidth) / dayWidth;
1206+
const daysDragged =
1207+
(roundToNearest(dragEndEvent.x, dayWidth) / dayWidth) *
1208+
(this.rtl ? -1 : 1);
11801209
const minutesMoved = useY
11811210
? getMinutesMoved(
11821211
dragEndEvent.y,
@@ -1292,10 +1321,11 @@ export class CalendarWeekViewComponent implements OnChanges, OnInit, OnDestroy {
12921321
),
12931322
};
12941323

1324+
const modifier = this.rtl ? -1 : 1;
1325+
12951326
if (typeof resizeEvent.edges.left !== 'undefined') {
1296-
const daysDiff = Math.round(
1297-
+resizeEvent.edges.left / this.dayColumnWidth
1298-
);
1327+
const daysDiff =
1328+
Math.round(+resizeEvent.edges.left / this.dayColumnWidth) * modifier;
12991329
const newStart = addDaysWithExclusions(
13001330
this.dateAdapter,
13011331
newEventDates.start,
@@ -1308,9 +1338,8 @@ export class CalendarWeekViewComponent implements OnChanges, OnInit, OnDestroy {
13081338
newEventDates.start = smallestResizes.start;
13091339
}
13101340
} else if (typeof resizeEvent.edges.right !== 'undefined') {
1311-
const daysDiff = Math.round(
1312-
+resizeEvent.edges.right / this.dayColumnWidth
1313-
);
1341+
const daysDiff =
1342+
Math.round(+resizeEvent.edges.right / this.dayColumnWidth) * modifier;
13141343
const newEnd = addDaysWithExclusions(
13151344
this.dateAdapter,
13161345
newEventDates.end,
@@ -1367,10 +1396,11 @@ export class CalendarWeekViewComponent implements OnChanges, OnInit, OnDestroy {
13671396
this.dayColumnWidth = this.getDayColumnWidth(eventsContainer);
13681397
const resizeHelper: CalendarResizeHelper = new CalendarResizeHelper(
13691398
eventsContainer,
1370-
minWidth
1399+
minWidth,
1400+
this.rtl
13711401
);
1372-
this.validateResize = ({ rectangle }) =>
1373-
resizeHelper.validateResize({ rectangle });
1402+
this.validateResize = ({ rectangle, edges }) =>
1403+
resizeHelper.validateResize({ rectangle: { ...rectangle }, edges });
13741404
this.cdr.markForCheck();
13751405
}
13761406
}

projects/angular-calendar/src/modules/week/calendar-week-view.scss

+60
Original file line numberDiff line numberDiff line change
@@ -18,10 +18,20 @@ $cal-week-view-vars: map-merge($cal-vars, $cal-week-view-vars);
1818
.cal-day-headers .cal-header {
1919
&:not(:last-child) {
2020
border-right-color: map-get($theme, border-color);
21+
22+
[dir='rtl'] & {
23+
border-right-color: initial;
24+
border-left: solid 1px map-get($theme, border-color) !important;
25+
}
2126
}
2227

2328
&:first-child {
2429
border-left-color: map-get($theme, border-color);
30+
31+
[dir='rtl'] & {
32+
border-left-color: initial;
33+
border-right-color: map-get($theme, border-color);
34+
}
2535
}
2636
}
2737

@@ -32,6 +42,11 @@ $cal-week-view-vars: map-merge($cal-vars, $cal-week-view-vars);
3242

3343
.cal-day-column {
3444
border-left-color: map-get($theme, border-color);
45+
46+
[dir='rtl'] & {
47+
border-left-color: initial;
48+
border-right-color: map-get($theme, border-color);
49+
}
3550
}
3651

3752
.cal-event {
@@ -92,6 +107,11 @@ $cal-week-view-vars: map-merge($cal-vars, $cal-week-view-vars);
92107
display: flex;
93108
padding-left: 70px;
94109
border: 1px solid;
110+
111+
[dir='rtl'] & {
112+
padding-left: initial;
113+
padding-right: 70px;
114+
}
95115
}
96116

97117
.cal-day-headers .cal-header {
@@ -101,10 +121,20 @@ $cal-week-view-vars: map-merge($cal-vars, $cal-week-view-vars);
101121

102122
&:not(:last-child) {
103123
border-right: 1px solid;
124+
125+
[dir='rtl'] & {
126+
border-right: initial;
127+
border-left: 1px solid;
128+
}
104129
}
105130

106131
&:first-child {
107132
border-left: 1px solid;
133+
134+
[dir='rtl'] & {
135+
border-left: initial;
136+
border-right: 1px solid;
137+
}
108138
}
109139
}
110140

@@ -116,11 +146,17 @@ $cal-week-view-vars: map-merge($cal-vars, $cal-week-view-vars);
116146
.cal-day-column {
117147
flex-grow: 1;
118148
border-left: solid 1px;
149+
150+
[dir='rtl'] & {
151+
border-left: initial;
152+
border-right: solid 1px;
153+
}
119154
}
120155

121156
.cal-event {
122157
font-size: 12px;
123158
border: 1px solid;
159+
direction: ltr;
124160
}
125161

126162
.cal-time-label-column {
@@ -155,6 +191,11 @@ $cal-week-view-vars: map-merge($cal-vars, $cal-week-view-vars);
155191
position: relative;
156192
height: 31px;
157193
margin-left: 70px;
194+
195+
[dir='rtl'] & {
196+
margin-left: initial;
197+
margin-right: 70px;
198+
}
158199
}
159200

160201
.cal-event-container {
@@ -178,11 +219,25 @@ $cal-week-view-vars: map-merge($cal-vars, $cal-week-view-vars);
178219
.cal-starts-within-week .cal-event {
179220
border-top-left-radius: 5px;
180221
border-bottom-left-radius: 5px;
222+
223+
[dir='rtl'] & {
224+
border-top-left-radius: initial;
225+
border-bottom-left-radius: initial;
226+
border-top-right-radius: 5px !important;
227+
border-bottom-right-radius: 5px !important;
228+
}
181229
}
182230

183231
.cal-ends-within-week .cal-event {
184232
border-top-right-radius: 5px;
185233
border-bottom-right-radius: 5px;
234+
235+
[dir='rtl'] & {
236+
border-top-right-radius: initial;
237+
border-bottom-right-radius: initial;
238+
border-top-left-radius: 5px;
239+
border-bottom-left-radius: 5px;
240+
}
186241
}
187242

188243
.cal-time-label-column {
@@ -201,6 +256,11 @@ $cal-week-view-vars: map-merge($cal-vars, $cal-week-view-vars);
201256

202257
&.cal-resize-handle-after-end {
203258
right: 0;
259+
260+
[dir='rtl'] & {
261+
right: initial;
262+
left: 0;
263+
}
204264
}
205265
}
206266
}

0 commit comments

Comments
 (0)