Skip to content

Commit eeca70c

Browse files
authored
Merge pull request #393 from mariohmol/fix/344-jquery-div-support
fix(#344): accept jQuery-wrapped elements in GanttChart constructor
2 parents 4d483d9 + 7e35e86 commit eeca70c

3 files changed

Lines changed: 99 additions & 2 deletions

File tree

dist/jsgantt.js

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,8 @@ var date_utils_1 = require("./utils/date_utils");
2626
* @param pFormat (required) - used to indicate whether chart should be drawn in "hour", "day", "week", "month", or "quarter" format
2727
*/
2828
var GanttChart = function (pDiv, pFormat) {
29-
this.vDiv = pDiv;
29+
// Accept either a native DOM element or a jQuery-wrapped element
30+
this.vDiv = (pDiv && pDiv[0] instanceof Element) ? pDiv[0] : pDiv;
3031
this.vFormat = pFormat;
3132
this.vDivId = null;
3233
this.vUseFade = 1;

src/draw.ts

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -30,7 +30,8 @@ import { parseDateFormatStr, getMinDate, coerceDate, getMaxDate, formatDateStr,
3030
* @param pFormat (required) - used to indicate whether chart should be drawn in "hour", "day", "week", "month", or "quarter" format
3131
*/
3232
export const GanttChart = function (pDiv, pFormat) {
33-
this.vDiv = pDiv;
33+
// Accept either a native DOM element or a jQuery-wrapped element
34+
this.vDiv = (pDiv && pDiv[0] instanceof Element) ? pDiv[0] : pDiv;
3435
this.vFormat = pFormat;
3536
this.vDivId = null;
3637
this.vUseFade = 1;
Lines changed: 95 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,95 @@
1+
/**
2+
* Unit tests for GanttChart constructor — jQuery-element normalisation.
3+
*
4+
* Issue #344: passing a jQuery-wrapped element threw "hasChildNodes is not a
5+
* function" because pDiv[0] (the real Element) was never unwrapped.
6+
*
7+
* PR #393 fixes this with the guard:
8+
* this.vDiv = (pDiv && pDiv[0] instanceof Element) ? pDiv[0] : pDiv;
9+
*/
10+
11+
import './helpers'; // DOM shim — must be first
12+
import { expect } from 'chai';
13+
14+
// GanttChart is exported as a plain constructor function.
15+
import { GanttChart } from '../../src/draw';
16+
17+
// ─── Minimal fake DOM element ─────────────────────────────────────────────────
18+
// The shim in helpers.ts installs document.createElement / createTextNode so
19+
// that TaskItem works. GanttChart only stores pDiv in this.vDiv, so a plain
20+
// object that satisfies `instanceof Element` suffices.
21+
22+
function makeFakeElement(): Element {
23+
// jsdom is not available; create a minimal stand-in that IS an Element by
24+
// delegating through the global.Element constructor set up in the shim.
25+
// However, `instanceof Element` requires the *global* Element constructor.
26+
// We set one up below so tests are self-contained.
27+
return new (global as any).Element();
28+
}
29+
30+
// Install a minimal Element constructor in the global scope so that
31+
// `pDiv[0] instanceof Element` works inside GanttChart.
32+
before(function () {
33+
if (!(global as any).Element) {
34+
(global as any).Element = class Element {
35+
nodeName = 'DIV';
36+
className = '';
37+
childNodes: any[] = [];
38+
hasChildNodes() { return this.childNodes.length > 0; }
39+
};
40+
}
41+
});
42+
43+
// ─── Tests ────────────────────────────────────────────────────────────────────
44+
45+
describe('GanttChart constructor — pDiv normalisation (issue #344)', () => {
46+
47+
it('stores a plain DOM element unchanged', () => {
48+
const el = makeFakeElement();
49+
const chart = new (GanttChart as any)(el, 'week');
50+
expect(chart.vDiv).to.equal(el);
51+
});
52+
53+
it('unwraps a jQuery-like object (pDiv[0] instanceof Element)', () => {
54+
const el = makeFakeElement();
55+
// Simulate a jQuery wrapper: array-like with [0] pointing to the element.
56+
const jqueryLike = { 0: el, length: 1 };
57+
const chart = new (GanttChart as any)(jqueryLike, 'week');
58+
expect(chart.vDiv).to.equal(el,
59+
'vDiv should be the unwrapped DOM element, not the jQuery wrapper');
60+
});
61+
62+
it('does NOT unwrap when pDiv[0] is not an Element', () => {
63+
// e.g. someone passes an arbitrary array-like whose [0] is a string
64+
const notAnElement = { 0: 'string-value', length: 1 };
65+
const chart = new (GanttChart as any)(notAnElement, 'week');
66+
expect(chart.vDiv).to.equal(notAnElement,
67+
'vDiv should remain unchanged when [0] is not an Element');
68+
});
69+
70+
it('handles null pDiv without throwing', () => {
71+
expect(() => new (GanttChart as any)(null, 'week')).to.not.throw();
72+
const chart = new (GanttChart as any)(null, 'week');
73+
expect(chart.vDiv).to.equal(null);
74+
});
75+
76+
it('handles undefined pDiv without throwing', () => {
77+
expect(() => new (GanttChart as any)(undefined, 'week')).to.not.throw();
78+
const chart = new (GanttChart as any)(undefined, 'week');
79+
// undefined is falsy → guard short-circuits → vDiv stays undefined
80+
expect(chart.vDiv).to.equal(undefined);
81+
});
82+
83+
it('stores the format string in vFormat', () => {
84+
const el = makeFakeElement();
85+
const chart = new (GanttChart as any)(el, 'month');
86+
expect(chart.vFormat).to.equal('month');
87+
});
88+
89+
it('stores the correct format when a jQuery wrapper is passed', () => {
90+
const el = makeFakeElement();
91+
const jqueryLike = { 0: el, length: 1 };
92+
const chart = new (GanttChart as any)(jqueryLike, 'day');
93+
expect(chart.vFormat).to.equal('day');
94+
});
95+
});

0 commit comments

Comments
 (0)