📄 jsgantt.js
字号:
vID = vList[i].getID();
vTaskDiv = document.getElementById("taskbar_"+vID);
vBarDiv = document.getElementById("bardiv_"+vID);
vParDiv = document.getElementById("childgrid_"+vID);
if(vBarDiv) {
vList[i].setStartX( vBarDiv.offsetLeft );
vList[i].setStartY( vParDiv.offsetTop+vBarDiv.offsetTop+6 );
vList[i].setEndX( vBarDiv.offsetLeft + vBarDiv.offsetWidth );
vList[i].setEndY( vParDiv.offsetTop+vBarDiv.offsetTop+6 );
}
}
}
this.AddTaskItem = function(value)
{
vTaskList.push(value);
}
this.getList = function() { return vTaskList };
this.setFormat = function(pFormat){ vFormat = pFormat; this.Draw(); };
this.getGraphics = function() {return gr;};
this.drawDependency =function(x1,y1,x2,y2)
{
var gr = this.getGraphics();
gr.penColor = "red";
if(x1 < x2)
{
gr.drawLine(x1,y1,x1+5,y1);
gr.drawLine(x1+5,y1,x1+5,y2);
gr.drawLine(x1+5,y2,x2,y2);
}
else
{
var Xpoints = new Array(x1,x1+5, x1+5, x2-5, x2-5,x2);
var Ypoints = new Array(y1,y1, y2-5, y2-5, y2,y2);
gr.drawLine(x1,y1,x1+5,y1);
gr.drawLine(x1+5,y1,x1+5,y2-10);
gr.drawLine(x1+5,y2-10,x2-5,y2-10);
gr.drawLine(x2-5,y2-10,x2-5,y2);
gr.drawLine(x2-5,y2,x2,y2);
}
}
this.DrawDependencies = function (){
//First recalculate the x,y
this.CalcTaskXY();
var gr = this.getGraphics();
gr.clear();
var vList = this.getList();
for(var i = 0; i < vList.length; i++)
{
if(!isNaN(vList[i].getDepend()) && document.getElementById("childgrid_"+vList[i].getID()).style.display=='')
{
var ii = this.getArrayLocationByID(vList[i].getDepend())
if(document.getElementById("childgrid_"+vList[ii].getID()).style.display=='')
{
this.drawDependency(vList[ii].getEndX(),vList[ii].getEndY(),vList[i].getStartX(),vList[i].getStartY())
}
}
}
}
this.getArrayLocationByID = function(pId) {
var vList = this.getList();
for(var i = 0; i < vList.length; i++)
{
if(vList[i].getID()==pId)
return i;
}
}
this.Draw = function()
{
var vCurrDate = new Date();
var vMaxDate = new Date();
var vMinDate = new Date();
var vTmpDate = new Date();
var vNxtDate = new Date();
var vTaskLeft = 0;
var vTaskRight = 0;
var vNumCols = 0;
var vID = 0;
var vMainTable = "";
var vLeftTable = "";
var vRightTable = "";
var vDateRowStr = "";
var vItemRowStr = "";
var vSpanSet = 0;
var vColWidth = 0;
var vColUnit = 0;
var vChartWidth = 0;
var vNumDays = 0;
var vDayWidth = 0;
var vStr = "";
if(vTaskList.length > 0)
{
vCurrDate.setFullYear(vCurrDate.getFullYear(), vCurrDate.getMonth(), vCurrDate.getDate());
// Process all tasks preset parent date and completion %
JSGantt.processRows(vTaskList, 0, -1, 1);
// get overall min/max dates plus padding
vMinDate = JSGantt.getMinDate(vTaskList, vFormat);
vMaxDate = JSGantt.getMaxDate(vTaskList, vFormat);
// Calculate chart width variables. vColWidth can be altered manually to change each column width
// May be smart to make this a parameter of GanttChart or set it based on existing pWidth parameter
if(vFormat == 'day') {
vColWidth = 18;
vColUnit = 1;
}
if(vFormat == 'week') {
vColWidth = 37;
vColUnit = 7;
}
if(vFormat == 'month') {
vColWidth = 37;
vColUnit = 30;
}
vNumDays = Math.ceil((Date.parse(vMaxDate) - Date.parse(vMinDate)) / ( 24 * 60 * 60 * 1000));
vNumUnits = vNumDays / vColUnit;
vChartWidth = vNumUnits * vColWidth + 1;
vDayWidth = (vColWidth / vColUnit) + (1/vColUnit);
vMainTable =
"<TABLE id=theTable cellSpacing=0 cellPadding=0 border=0><TBODY><TR>" +
"<TD vAlign=top bgColor=#ffffff>";
// DRAW the Left-side of the chart (names, resources, comp%)
vLeftTable =
'<DIV class=scroll id=leftside style="width:445"><TABLE cellSpacing=0 cellPadding=0 border=0><TBODY>' +
'<TR style="HEIGHT: 17px">' +
' <TD style="WIDTH: 5px; HEIGHT: 17px"></TD>' +
' <TD style="WIDTH: 240px; HEIGHT: 17px"><NOBR></NOBR></TD>' +
' <TD style="WIDTH: 16px; HEIGHT: 17px"></TD>' +
' <TD style="WIDTH: 60px; HEIGHT: 17px"></TD></TR>' +
'<TR style="HEIGHT: 20px">' +
' <TD style="BORDER-TOP: #efefef 1px solid; WIDTH: 15px; HEIGHT: 20px"></TD>' +
' <TD style="BORDER-TOP: #efefef 1px solid; WIDTH: 250px; HEIGHT: 20px"><NOBR></NOBR></TD>' +
' <TD style="BORDER-TOP: #efefef 1px solid; FONT-SIZE: 12px; BORDER-LEFT: #efefef 1px solid; WIDTH: 60px; HEIGHT: 20px" align=middle nowrap>Resource</TD>' +
' <TD style="BORDER-TOP: #efefef 1px solid; FONT-SIZE: 12px; BORDER-LEFT: #efefef 1px solid; WIDTH: 60px; HEIGHT: 20px" align=middle nowrap>Duration</TD>' +
' <TD style="BORDER-TOP: #efefef 1px solid; FONT-SIZE: 12px; BORDER-LEFT: #efefef 1px solid; WIDTH: 60px; HEIGHT: 20px" align=middle nowrap>% Comp.</TD>' +
'</TR>';
for(i = 0; i < vTaskList.length; i++)
{
vID = vTaskList[i].getID();
vLeftTable +=
'<TR id=child_' + vID + '>' +
' <TD class=gdatehead style="WIDTH: 15px; HEIGHT: 20px; BORDER-TOP: #efefef 1px solid; FONT-SIZE: 12px; BORDER-LEFT: #efefef 1px solid;"> </TD>' +
' <TD class=gname style="WIDTH: 250px; HEIGHT: 20px; BORDER-TOP: #efefef 1px solid; FONT-SIZE: 12px;" nowrap><NOBR><span style="color: #aaaaaa">';
for(j=1; j<vTaskList[i].getLevel(); j++) {
vLeftTable += ' | ';
}
vLeftTable += '</span>';
if( vTaskList[i].getGroup()) {
if (JSGantt.isIE()) // IE;
vLeftTable += '<SPAN id="group_' + vID + '" style="color:#aaaaaa; cursor:pointer; font:bold;" onclick="JSGantt.folder(' + vID + ','+vGanttVar+');'+vGanttVar+'.DrawDependencies();"> v</span><span style="color:#aaaaaa">-"  </SPAN>' ;
else
vLeftTable += '<SPAN id="group_' + vID + '" style="color:#aaaaaa; cursor:pointer; font:bold;" onclick="JSGantt.folder(' + vID + ','+vGanttVar+');'+vGanttVar+'.DrawDependencies();">v</span><span style="color:#aaaaaa">-"  </SPAN>' ;
} else {
vLeftTable += '<span style="color: #aaaaaa"> |-" </span>';
}
vLeftTable +=
'<span onclick=JSGantt.taskLink("' + vTaskList[i].getLink() + '"); style="cursor:pointer">' + vTaskList[i].getName() + '</span></NOBR></TD>' +
' <TD class=gname style="WIDTH: 60px; HEIGHT: 20px; TEXT-ALIGN: center; BORDER-TOP: #efefef 1px solid; FONT-SIZE: 12px; BORDER-LEFT: #efefef 1px solid;" align=middle nowrap>' + vTaskList[i].getResource() + '</TD>' +
' <TD class=gname style="WIDTH: 60px; HEIGHT: 20px; TEXT-ALIGN: center; BORDER-TOP: #efefef 1px solid; FONT-SIZE: 12px; BORDER-LEFT: #efefef 1px solid;" align=middle nowrap>' + vTaskList[i].getDuration(vFormat) + '</TD>' +
' <TD class=gname style="WIDTH: 60px; HEIGHT: 20px; TEXT-ALIGN: center; BORDER-TOP: #efefef 1px solid; FONT-SIZE: 12px; BORDER-LEFT: #efefef 1px solid;" align=middle nowrap>' + vTaskList[i].getCompStr() + '</TD>' +
'</TR>';
}
// DRAW the date format selector at bottom left. Another potential GanttChart parameter to hide/show this selector
vLeftTable += '</TD></TR>' +
'<TR><TD border=1 colspan=5 align=left style="BORDER-TOP: #efefef 1px solid; FONT-SIZE: 11px; BORDER-LEFT: #efefef 1px solid; height=18px"> Powered by <a href=http://www.cujava.com>cujava.com</a> Format:';
if (vFormat=='day') vLeftTable += '<INPUT TYPE=RADIO NAME="radFormat" VALUE="day" checked>天';
else vLeftTable += '<INPUT TYPE=RADIO NAME="radFormat" onclick=JSGantt.changeFormat("day",'+vGanttVar+'); VALUE="day">天';
if (vFormat=='week') vLeftTable += '<INPUT TYPE=RADIO NAME="radFormat" VALUE="week" checked>周';
else vLeftTable += '<INPUT TYPE=RADIO NAME="radFormat" onclick=JSGantt.changeFormat("week",'+vGanttVar+') VALUE="week">周';
if (vFormat=='month') vLeftTable += '<INPUT TYPE=RADIO NAME="radFormat" checked>月';
else vLeftTable += '<INPUT TYPE=RADIO NAME="radFormat" onclick=JSGantt.changeFormat("month",'+vGanttVar+') VALUE="month">月';
vLeftTable += '</TD></TR></TBODY></TABLE></TD>';
vMainTable += vLeftTable;
// Draw the Chart Rows
vRightTable =
'<TD style="width: ' + vChartWidth + 'px;" vAlign=top bgColor=#ffffff>' +
'<DIV class=scroll2 id=rightside>' +
'<TABLE style="width: ' + vChartWidth + 'px;" cellSpacing=0 cellPadding=0 border=0>' +
'<TBODY><TR style="HEIGHT: 18px">';
vTmpDate.setFullYear(vMinDate.getFullYear(), vMinDate.getMonth(), vMinDate.getDate());
// Major Date Header
while(Date.parse(vTmpDate) <= Date.parse(vMaxDate))
{
vStr = vTmpDate.getFullYear() + '';
vStr = vStr.substring(2,4);
if(vFormat == 'day')
{
vRightTable += '<td class=gdatehead style="FONT-SIZE: 12px; HEIGHT: 19px;" align=center colspan=7>' + (vTmpDate.getMonth()+1) + '/' + vTmpDate.getDate() + ' - ';
vTmpDate.setDate(vTmpDate.getDate()+6);
vRightTable += (vTmpDate.getMonth()+1) + '/' + vTmpDate.getDate() + '/' + vStr + '</td>';
vTmpDate.setDate(vTmpDate.getDate()+1);
}
if(vFormat == 'week')
{
vRightTable += '<td class=gdatehead align=center style="FONT-SIZE: 12px; HEIGHT: 19px;" width='+vColWidth+'>`'+ vStr + '</td>';
vTmpDate.setDate(vTmpDate.getDate()+7);
}
if(vFormat == 'month')
{
vRightTable += '<td class=gdatehead align=center style="FONT-SIZE: 12px; HEIGHT: 19px;" width='+vColWidth+'>`'+ vStr + '</td>';
vTmpDate.setDate(vTmpDate.getDate() + 1);
while(vTmpDate.getDate() > 1)
{
vTmpDate.setDate(vTmpDate.getDate() + 1);
}
}
}
vRightTable += '</TR><TR>';
// Minor Date header and Cell Rows
vTmpDate.setFullYear(vMinDate.getFullYear(), vMinDate.getMonth(), vMinDate.getDate());
vNxtDate.setFullYear(vMinDate.getFullYear(), vMinDate.getMonth(), vMinDate.getDate());
vNumCols = 0;
while(Date.parse(vTmpDate) <= Date.parse(vMaxDate))
{
if(vFormat == 'day')
{
if(vTmpDate.getDay() % 6 == 0) {
vDateRowStr += '<td class="gheadwkend" style="BORDER-TOP: #efefef 1px solid; FONT-SIZE: 12px; HEIGHT: 19px; BORDER-LEFT: #efefef 1px solid;" bgcolor=#cfcfcf align=middle><div style="width: '+vColWidth+'">' + vTmpDate.getDate() + '</div></td>';
vItemRowStr += '<td class="gheadwkend" style="BORDER-TOP: #efefef 1px solid; FONT-SIZE: 12px; BORDER-LEFT: #efefef 1px solid; cursor: default;" bgcolor=#cfcfcf align=middle><div style="width: '+vColWidth+'"> </div></td>';
}
else {
vDateRowStr += '<td class="ghead" style="BORDER-TOP: #efefef 1px solid; FONT-SIZE: 12px; HEIGHT: 19px; BORDER-LEFT: #efefef 1px solid;" align=middle><div style="width: '+vColWidth+'">' + vTmpDate.getDate() + '</div></td>';
vItemRowStr += '<td class="ghead" style="BORDER-TOP: #efefef 1px solid; FONT-SIZE: 12px; BORDER-LEFT: #efefef 1px solid; cursor: default;" align=middle><div style="width: '+vColWidth+'">  </div></td>';
}
vTmpDate.setDate(vTmpDate.getDate() + 1);
}
if(vFormat == 'week')
{
vNxtDate.setDate(vNxtDate.getDate() + 7);
if(vNxtDate <= vMaxDate) {
vDateRowStr += '<td class="ghead" style="BORDER-TOP: #efefef 1px solid; FONT-SIZE: 12px; HEIGHT: 19px; BORDER-LEFT: #efefef 1px solid;" align=middle width:'+vColWidth+'><div style="width: '+vColWidth+'">' + (vTmpDate.getMonth()+1) + '/' + vTmpDate.getDate() + '</div></td>';
vItemRowStr += '<td class="ghead" style="BORDER-TOP: #efefef 1px solid; FONT-SIZE: 12px; BORDER-LEFT: #efefef 1px solid;" align=middle><div style="width: '+vColWidth+'">  </div></td>';
} else {
vDateRowStr += '<td class="ghead" style="BORDER-TOP: #efefef 1px solid; FONT-SIZE: 12px; HEIGHT: 19px; BORDER-LEFT: #efefef 1px solid; BORDER-RIGHT: #efefef 1px solid;" align=middle width:'+vColWidth+'><div style="width: '+vColWidth+'">' + (vTmpDate.getMonth()+1) + '/' + vTmpDate.getDate() + '</div></td>';
vItemRowStr += '<td class="ghead" style="BORDER-TOP: #efefef 1px solid; FONT-SIZE: 12px; BORDER-LEFT: #efefef 1px solid; BORDER-RIGHT: #efefef 1px solid;" align=middle><div style="width: '+vColWidth+'">  </div></td>';
}
vTmpDate.setDate(vTmpDate.getDate() + 7);
}
if(vFormat == 'month')
{
vNxtDate.setDate(vNxtDate.getDate() + 31);
if(vNxtDate <= vMaxDate) {
vDateRowStr += '<td class="ghead" style="BORDER-TOP: #efefef 1px solid; FONT-SIZE: 12px; HEIGHT: 19px; BORDER-LEFT: #efefef 1px solid;" align=middle width:'+vColWidth+'><div style="width: '+vColWidth+'">' + month[vTmpDate.getMonth()].substr(0,3) + '</div></td>';
vItemRowStr += '<td class="ghead" style="BORDER-TOP: #efefef 1px solid; FONT-SIZE: 12px; BORDER-LEFT: #efefef 1px solid;" align=middle><div style="width: '+vColWidth+'">  </div></td>';
} else {
vDateRowStr += '<td class="ghead" style="BORDER-TOP: #efefef 1px solid; FONT-SIZE: 12px; HEIGHT: 19px; BORDER-LEFT: #efefef 1px solid; BORDER-RIGHT: #efefef 1px solid;" align=middle width:'+vColWidth+'><div style="width: '+vColWidth+'">' + month[vTmpDate.getMonth()].substr(0,3) + '</div></td>';
vItemRowStr += '<td class="ghead" style="BORDER-TOP: #efefef 1px solid; FONT-SIZE: 12px; BORDER-LEFT: #efefef 1px solid; BORDER-RIGHT: #efefef 1px solid;" align=middle><div style="width: '+vColWidth+'">  </div></td>';
}
vTmpDate.setDate(vTmpDate.getDate() + 1);
while(vTmpDate.getDate() > 1)
{
vTmpDate.setDate(vTmpDate.getDate() + 1);
}
}
}
vRightTable += vDateRowStr + '</TR>';
vRightTable += '</TBODY></TABLE>';
// Draw each row
for(i = 0; i < vTaskList.length; i++)
{
vTmpDate.setFullYear(vMinDate.getFullYear(), vMinDate.getMonth(), vMinDate.getDate());
vTaskStart = vTaskList[i].getStart();
vTaskEnd = vTaskList[i].getEnd();
vNumCols = 0;
vID = vTaskList[i].getID();
vNumUnits = Math.ceil((vTaskList[i].getEnd() - vTaskList[i].getStart()) / (24 * 60 * 60 * 1000)) + 1;
vSpanSet = 0;
vRightTable += '<DIV id=childgrid_' + vID + ' class=yesdisplay style="position:relative">';
vRightTable += '<DIV><TABLE style="position:relative; top:0px; width: ' + vChartWidth + 'px;" cellSpacing=0 cellPadding=0 border=0><TR class=yesdisplay style="HEIGHT: 20px">' + vItemRowStr + '</TR></TABLE></DIV>';
if( vTaskList[i].getMile()) {
// Build date string for Title
vStr = vTaskStart.getFullYear() + '';
vStr = vStr.substring(2,4);
vDateRowStr = vTaskStart.getMonth() + '/' + vTaskStart.getDate() + '/' + vStr;
vTaskLeft = (Date.parse(vTaskList[i].getStart()) - Date.parse(vMinDate)) / (24 * 60 * 60 * 1000);
vTaskRight = 1
vRightTable +=
'<div id=bardiv_' + vID + ' style="position:absolute; top:0px; left:' + Math.ceil((vTaskLeft * (vDayWidth) + 1)) + 'px; height: 16px; width:12px; overflow:hidden;">' +
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -