#include "stdafx.h" #include "AcDbObjectPtr.h" #include "AcGiUtil.h" #include "dbobjptr.h" #include "dbGridSheet.h" #include "layerdef.h" #include "GeCurveInline.h" #include "SHArray.h" #include "AecDbMtext.h" #include "TBlockGeomInfo.h" AcDbObjectId InitBlock(const TCHAR *pszBlock, AcDbDatabase *pDb = NULL); static int CompareRange(const GridRange *p1, const void *p2) { return (p1 != p2); } #define LSF_DEFAULT 0.4 Acad::ErrorStatus CalInsertParameters(const AcDbBlockReference *pBlkSrc, XPoint &ptNewBase, double *nRotation, double *nSx, double *nSy, double *nSz, BlockGeomInfo info) { ads_matrix matRotOld, matMove, matScale, matRotNew, matTransform; double nSizeX, nSizeY, nSizeZ, nRot; XPoint ptBase, ptCen, ptNewCen; VERIFY(GlobalFunc::GetBlockRefSizeInfo(pBlkSrc, ptBase, &nRot, ptCen, &nSizeX, &nSizeY, &nSizeZ) == RTNORM); ptNewCen = info.m_ptCen; ptNewCen.z += info.m_nSizeZ / 2.0; // 绕旧中心旋转-nRotOld -> 绕旧中心Scale -> 平移到新中心 -> 旋转 RotNew // or // 绕旧中心旋转-nRotOld -> 绕旧中心Scale -> 旋转 RotNew -> 平移到新中心 (Current Method) AcGeScale3d bScale = pBlkSrc->scaleFactors(); double sx = 1, sy = 1, sz = 1; if (fabs(nSizeX) > 1.0E-6) bScale[0] *= (sx = info.m_nSizeX / nSizeX); if (fabs(nSizeY) > 1.0E-6) bScale[1] *= (sy = info.m_nSizeY / nSizeY); if (fabs(nSizeZ) > 1.0E-6) bScale[2] *= (sz = info.m_nSizeZ / nSizeZ); ptCen.GetRotationMatrix(-nRot, matRotOld); ptCen.GetScaleMatrix(sx, sy, sz, matScale); ptCen.GetRotationMatrix(info.m_nRotation, matRotNew); ptCen.GetMoveMatrix(ptNewCen, matMove); GlobalFunc::MatrixMultiply(matTransform, matMove, matRotNew, matScale, matRotOld, NULL); ptNewBase = ptBase.TransformAs(matTransform); //换算新的基点位置 *nRotation = info.m_nRotation; *nSx = bScale[0]; *nSy = bScale[1]; *nSz = bScale[2]; return Acad::eOk; } void UpdateInsert(AcDbBlockReference *pInsert, BlockGeomInfo info, BOOL bUniScale) { XPoint ptNewBase; double nNewRot; AcGeScale3d scale; if (CalInsertParameters(pInsert, ptNewBase, &nNewRot, &scale[0], &scale[1], &scale[2], info) != Acad::eOk) return; pInsert->setPosition(ptNewBase); pInsert->setRotation(nNewRot); if (bUniScale) { double dScale = min(scale[0], scale[1]); pInsert->setScaleFactors(AcGeScale3d(dScale, dScale, dScale)); } else { pInsert->setScaleFactors(scale); } } //////////////////////////////////////////// // 方格的样式 //TArch5\6,1;TArch7,2 const Adesk::UInt8 GridStyle::g_nVersion = 2; GridStyle::GridStyle() { m_nOverride = 0; //override parent's style (none) m_nHorMode = AcDb::kTextLeft; // Specifies the horizontal text alignment m_nVerMode = AcDb::kTextBase; // AcDbHardPointerId m_idTextStyle; // Font m_nTextColor = 0; //Controls the foreground(Text) color m_bTextWrap = true; // Word wraps cell text when true m_nLineSpaceFactor = LSF_DEFAULT; //自动换行时的行距系数(行距=系数*字高) m_nTextHeight = 3.0; m_nTextDirection = kRight; } GridStyle::GridStyle(const GridStyle &src) { *this = src; } GridStyle & GridStyle::operator = (const GridStyle &src) { GlobalFunc::CopyObject(src, *this); return *this; } Acad::ErrorStatus GridStyle::dwgInFields(AcDbDwgFiler* pFiler) { Adesk::UInt8 nVer = 0; pFiler->readItem(&nVer); if (nVer > g_nVersion) // Version is too new return Acad::eMakeMeProxy; pFiler->readItem(&m_nOverride); if (m_nOverride & OF_HORMODE) { Adesk::UInt8 align; pFiler->readItem(&align); m_nHorMode = (AcDb::TextHorzMode)align; } if (m_nOverride & OF_VERMODE) { Adesk::UInt8 align; pFiler->readItem(&align); m_nVerMode = (AcDb::TextVertMode)align; } if (m_nOverride & OF_TEXTSTYLE) { pFiler->readItem(&m_idTextStyle); } if (m_nOverride & OF_TEXTCOLOR) { pFiler->readItem(&m_nTextColor); } if (m_nOverride & OF_TEXTWRAP) { pFiler->readItem(&m_bTextWrap); } if (m_nOverride & OF_LINESPACE) { pFiler->readItem(&m_nLineSpaceFactor); } if (m_nOverride & OF_TEXTHEIGHT) { pFiler->readItem(&m_nTextHeight); } if (nVer > 1) { Adesk::UInt8 nDirection; pFiler->readItem(&nDirection); m_nTextDirection = (TextDirection)nDirection; } return pFiler->filerStatus(); } Acad::ErrorStatus GridStyle::dwgOutFields(AcDbDwgFiler* pFiler) const { //if (g_nSaveTArchVer < 7) // pFiler->writeItem((Adesk::UInt8)1); //else pFiler->writeItem(g_nVersion); pFiler->writeItem(m_nOverride); if (m_nOverride & OF_HORMODE) pFiler->writeItem((Adesk::UInt8)m_nHorMode); if (m_nOverride & OF_VERMODE) pFiler->writeItem((Adesk::UInt8)m_nVerMode); if (m_nOverride & OF_TEXTSTYLE) pFiler->writeItem(m_idTextStyle); if (m_nOverride & OF_TEXTCOLOR) pFiler->writeItem(m_nTextColor); if (m_nOverride & OF_TEXTWRAP) pFiler->writeItem(m_bTextWrap); if (m_nOverride & OF_LINESPACE) pFiler->writeItem(m_nLineSpaceFactor); if (m_nOverride & OF_TEXTHEIGHT) pFiler->writeItem(m_nTextHeight); //if (g_nSaveTArchVer > 6) pFiler->writeItem((Adesk::UInt8)m_nTextDirection); return pFiler->filerStatus(); } void GridStyle::SetOverrideAll(BOOL bTrue) { if (bTrue) m_nOverride = (OF_HORMODE | OF_VERMODE | OF_TEXTSTYLE | OF_TEXTCOLOR | OF_TEXTWRAP | OF_LINESPACE | OF_TEXTHEIGHT); else m_nOverride = 0; } void GridStyle::SetFlagBit(int nFlag, BOOL bSet) { if (bSet) { m_nOverride |= nFlag; } else { m_nOverride &= ~nFlag; } } void GridStyle::SetTextStyleId(AcDbObjectId id) { m_idTextStyle = id; } void GridStyle::SetTextColor(Adesk::UInt16 nColor) { m_nTextColor = nColor; } void GridStyle::SetTextWrap(BOOL bTrue) { m_bTextWrap = bTrue; } void GridStyle::SetLineSpaceFactor(double nFactor) { m_nLineSpaceFactor = nFactor; } void GridStyle::SetTextHeight(double h) { m_nTextHeight = h; } BOOL GridStyle::TestFlagBit(int nFlag) const { return ((m_nOverride & nFlag) != 0); } AcDbObjectId GridStyle::GetTextStyleId() const { return m_idTextStyle; } Adesk::UInt16 GridStyle::GetTextColor() const { return m_nTextColor; } BOOL GridStyle::IsTextWrap() const { return m_bTextWrap; } double GridStyle::GetLineSpaceFactor() const { return m_nLineSpaceFactor; } double GridStyle::GetTextHeight() const { return m_nTextHeight; } void GridStyle::SetVerMode(AcDb::TextVertMode nVerMode) { m_nVerMode = nVerMode; } void GridStyle::SetHorMode(AcDb::TextHorzMode nHorMode) { m_nHorMode = nHorMode; } AcDb::TextHorzMode GridStyle::GetHorMode() const { return m_nHorMode; } AcDb::TextVertMode GridStyle::GetVerMode() const { return m_nVerMode; } ///////////////////////////////////// // 分割线样式 const Adesk::UInt8 DividerStyle::g_nVersion = 1; DividerStyle::DividerStyle() { m_nFlag = kParent; m_nColor = 0; //AcDbHardPointerId m_idLineType; //线型 m_nLineWidth = 0.0; //线宽 } DividerStyle::DividerStyle(const DividerStyle &src) { *this = src; } DividerStyle & DividerStyle::operator= (const DividerStyle &src) { GlobalFunc::CopyObject(src, *this); return *this; } Acad::ErrorStatus DividerStyle::dwgInFields(AcDbDwgFiler* pFiler) { Adesk::UInt8 nVer = 0; pFiler->readItem(&nVer); if (nVer > g_nVersion) // Version is too new return Acad::eMakeMeProxy; Adesk::UInt8 nTemp; pFiler->readItem(&nTemp); m_nFlag = (TDividerFlag)nTemp; if (m_nFlag == DividerStyle::kLocal) { pFiler->readItem(&m_nColor); pFiler->readItem(&m_idLineType); pFiler->readItem(&m_nLineWidth); } return pFiler->filerStatus(); } Acad::ErrorStatus DividerStyle::dwgOutFields(AcDbDwgFiler* pFiler) const { pFiler->writeItem(g_nVersion); pFiler->writeItem((Adesk::UInt8)m_nFlag); if (m_nFlag == DividerStyle::kLocal) { pFiler->writeItem(m_nColor); pFiler->writeItem(m_idLineType); pFiler->writeItem(m_nLineWidth); } return pFiler->filerStatus(); } DividerStyle::TDividerFlag DividerStyle::GetDividerFlag() const { return m_nFlag; } double DividerStyle::GetLineWidth() const { return m_nLineWidth; } AcDbObjectId DividerStyle::GetLineTypeId() const { return m_idLineType; } Adesk::UInt16 DividerStyle::GetColor() const { return m_nColor; } void DividerStyle::SetDividerFlag(TDividerFlag flag) { m_nFlag = flag; } void DividerStyle::SetLineWidth(double nWidth) { m_nLineWidth = nWidth; } void DividerStyle::SetLineTypeId(AcDbObjectId id) { m_idLineType = id; } void DividerStyle::SetColor(Adesk::UInt16 nColor) { m_nColor = nColor; } //////////////////////////////// // 列定义 const Adesk::UInt8 SheetColumn::g_nVersion = 1; SheetColumn::SheetColumn() { //m_gridStyle.m_nOverride = 0; m_divider.m_nFlag = DividerStyle::kParent; // Divider style for right column border m_bAllowSizing = true; // Enables interactive resizing for a column m_nWidth = 0.0; //in Paper Unit } SheetColumn::SheetColumn(const SheetColumn &src) { *this = src; } SheetColumn & SheetColumn::operator= (const SheetColumn &src) { GlobalFunc::CopyObject(src, *this); return *this; } BOOL SheetColumn::IsValid() const { return (m_nWidth > 0.0); } Acad::ErrorStatus SheetColumn::dwgInFields(AcDbDwgFiler* pFiler) { Adesk::UInt8 nVer = 0; pFiler->readItem(&nVer); if (nVer > g_nVersion) // Version is too new return Acad::eMakeMeProxy; Acad::ErrorStatus es = m_gridStyle.dwgInFields(pFiler); if (es != Acad::eOk) return es; es = m_divider.dwgInFields(pFiler); if (es != Acad::eOk) return es; pFiler->readItem(&m_bAllowSizing); pFiler->readItem(&m_nWidth); return pFiler->filerStatus(); } Acad::ErrorStatus SheetColumn::dwgOutFields(AcDbDwgFiler* pFiler) const { pFiler->writeItem(g_nVersion); VERIFY(m_gridStyle.dwgOutFields(pFiler) == Acad::eOk); VERIFY(m_divider.dwgOutFields(pFiler) == Acad::eOk); pFiler->writeItem(m_bAllowSizing); pFiler->writeItem(m_nWidth); return pFiler->filerStatus(); } //图纸单位 double SheetColumn::GetWidth() const { return m_nWidth; } //图纸单位 void SheetColumn::SetWidth(double w) { m_nWidth = w; } const DividerStyle & SheetColumn::GetDividerStyle() const { return m_divider; } DividerStyle & SheetColumn::GetDividerStyle() { return m_divider; } const GridStyle & SheetColumn::GetGridStyle() const { return m_gridStyle; } GridStyle & SheetColumn::GetGridStyle() { return m_gridStyle; } BOOL SheetColumn::AllowSizing() const { return m_bAllowSizing; } void SheetColumn::SetAllowSizing(BOOL bTrue) { m_bAllowSizing = bTrue; } void SheetColumn::SeDividerStyle(const DividerStyle &style) { GlobalFunc::CopyObject(style, m_divider); } void SheetColumn::SetGridStyle(const GridStyle &style) { GlobalFunc::CopyObject(style, m_gridStyle); } /////////////////////////////// // 行定义 const Adesk::UInt8 SheetRow::g_nVersion = 1; SheetRow::SheetRow() { m_divider.m_nFlag = DividerStyle::kParent; // Divider style for right column border m_nHeightFlag = SheetRow::kParent; // Disable interactive resizing for row m_nHeight = 0.0; //in Paper Unit m_nVerMode = AcDb::kTextBase; } SheetRow::SheetRow(const SheetRow &src) { *this = src; } SheetRow & SheetRow::operator= (const SheetRow &src) { GlobalFunc::CopyObject(src, *this); return *this; } double SheetRow::GetHeight() const { return m_nHeight; } void SheetRow::SetHeight(double h) { m_nHeight = h; } SheetRow::TRowHeightStyle SheetRow::GetRowHeightStyle() const { return m_nHeightFlag; } void SheetRow::SetRowHeightStyle(SheetRow::TRowHeightStyle st) { m_nHeightFlag = st; } const DividerStyle & SheetRow::GetDividerStyle() const { return m_divider; } DividerStyle & SheetRow::GetDividerStyle() { return m_divider; } void SheetRow::SeDividerStyle(const DividerStyle &src) { GlobalFunc::CopyObject(src, m_divider); } Acad::ErrorStatus SheetRow::dwgInFields(AcDbDwgFiler* pFiler) { Adesk::UInt8 nVer = 0; pFiler->readItem(&nVer); if (nVer > g_nVersion) // Version is too new return Acad::eMakeMeProxy; Acad::ErrorStatus es = m_divider.dwgInFields(pFiler); if (es != Acad::eOk) return es; Adesk::UInt8 nTemp; pFiler->readItem(&nTemp); m_nHeightFlag = (TRowHeightStyle)nTemp; pFiler->readItem(&m_nHeight); pFiler->readItem(&nTemp); m_nVerMode = (AcDb::TextVertMode)nTemp; return pFiler->filerStatus(); } Acad::ErrorStatus SheetRow::dwgOutFields(AcDbDwgFiler* pFiler) const { pFiler->writeItem(g_nVersion); VERIFY(m_divider.dwgOutFields(pFiler) == Acad::eOk); pFiler->writeItem((Adesk::UInt8)m_nHeightFlag); pFiler->writeItem(m_nHeight); pFiler->writeItem((Adesk::UInt8)m_nVerMode); return pFiler->filerStatus(); } AcDb::TextVertMode SheetRow::GetVerMode() const { return m_nVerMode; } void SheetRow::SetVerMode(AcDb::TextVertMode nVerMode) { m_nVerMode = nVerMode; } /////////////////////////////////// // 单元格的定义 //TArch6:1,TArch7:2 const Adesk::UInt8 GridCell::g_nVersion = 2; GridCell::GridCell() { //m_gridStyle.m_nOverride=0; m_pRange = NULL; //m_sText; } GridCell::GridCell(const GridCell &src) { *this = src; } GridCell & GridCell::operator = (const GridCell &src) { GlobalFunc::CopyObject(src.m_gridStyle, m_gridStyle); m_sText = src.m_sText; m_idBlock = src.m_idBlock; m_pRange = src.m_pRange; return *this; } Acad::ErrorStatus GridCell::dwgInFields(AcDbDwgFiler* pFiler, const DList *ranges) { Adesk::UInt8 nVer = 0; pFiler->readItem(&nVer); if (nVer > g_nVersion) // Version is too new return Acad::eMakeMeProxy; Adesk::UInt16 nRange = 0; pFiler->readItem(&nRange); if (nRange == 0 || !ranges) { m_pRange = NULL; Acad::ErrorStatus es = m_gridStyle.dwgInFields(pFiler); if (es != Acad::eOk) return es; GlobalFunc::ReadString(pFiler, m_sText); } else { DList *pRangeList = (DList *)ranges; m_pRange = (*pRangeList)[nRange - 1]; } if (nVer > 1) pFiler->readItem(&m_idBlock); return pFiler->filerStatus(); } Acad::ErrorStatus GridCell::dwgOutFields(AcDbDwgFiler* pFiler, const DList *ranges) const { //if (g_nSaveTArchVer < 7) // pFiler->writeItem((Adesk::UInt8)1); //else pFiler->writeItem(g_nVersion); Adesk::UInt16 nRange = 0; if (m_pRange && ranges) { DList *pRangeList = (DList *)ranges; if (pRangeList->FindNode(m_pRange, CompareRange)) { nRange = pRangeList->CurPosition() + 1; } } pFiler->writeItem(nRange); if (nRange == 0) { VERIFY(m_gridStyle.dwgOutFields(pFiler) == Acad::eOk); pFiler->writeString(m_sText); } //if (g_nSaveTArchVer > 6) pFiler->writeItem(m_idBlock); return pFiler->filerStatus(); } BOOL GridCell::IsRange() const { return (m_pRange != NULL); } const GridStyle & GridCell::GetGridStyle() const { if (m_pRange) return m_pRange->GetGridStyle(); return m_gridStyle; } GridStyle & GridCell::GetGridStyle() { if (m_pRange) return m_pRange->GetGridStyle(); return m_gridStyle; } const TCHAR *GridCell::GetText() const { if (m_pRange) return m_pRange->GetText(); return (const TCHAR *)m_sText; } void GridCell::SetText(const TCHAR *szText) { if (m_pRange) m_pRange->SetText(szText); m_sText = szText; CellBlockInsert insert; if (insert.ParserDesc(m_sText)) m_idBlock = InitBlock(insert.m_sBlockName); else m_idBlock = AcDbObjectId::kNull; } const GridRange * GridCell::GetRange() const { return m_pRange; } void GridCell::SetGridStyle(const GridStyle &style) { if (m_pRange) m_pRange->SetGridStyle(style); GlobalFunc::CopyObject(style, m_gridStyle); } void GridCell::SetRange(GridRange *pRange) { m_pRange = pRange; } /////////////////////////////////// // 合并单元格的定义 // Modify on 2003/6/24,8位整数上升到16位整数 const Adesk::UInt8 GridRange::g_nVersion = 2; GridRange::GridRange() { //m_gridStyle.m_nOverride=0; m_nRow = m_nColumn = -1; m_nRowMax = m_nColumnMax = -1; //m_sText; } GridRange::GridRange(const GridRange &src) { *this = src; } GridRange & GridRange::operator = (const GridRange &src) { GlobalFunc::CopyObject(src, *this); SetRange((GridRange *)src.GetRange()); return *this; } BOOL GridRange::IsValid() const { BOOL bRet = (m_nRow >= 0 && m_nColumn >= 0); bRet = (bRet && (m_nRowMax >= m_nRow && m_nColumnMax >= m_nColumn)); return bRet; } BOOL GridRange::IsCellar() const { return (m_nRow == m_nRowMax && m_nColumn == m_nColumnMax); } Acad::ErrorStatus GridRange::dwgInFields(AcDbDwgFiler* pFiler) { Acad::ErrorStatus es = GridCell::dwgInFields(pFiler); if (es != Acad::eOk) return es; Adesk::UInt8 nVer = 0; pFiler->readItem(&nVer); if (nVer > g_nVersion) // Version is too new return Acad::eMakeMeProxy; //Acad::ErrorStatus es=m_gridStyle.dwgInFields(pFiler); //if(es!=Acad::eOk) // return es; //ReadString(pFiler, m_sText); if (nVer < 2) { Adesk::UInt8 a1 = 0, a2 = 0, a3 = 0, a4 = 0; pFiler->readItem(&a1); pFiler->readItem(&a2); pFiler->readItem(&a3); pFiler->readItem(&a4); m_nRow = a1; m_nColumn = a2; m_nRowMax = a3; m_nColumnMax = a4; } else { pFiler->readItem(&m_nRow); pFiler->readItem(&m_nColumn); pFiler->readItem(&m_nRowMax); pFiler->readItem(&m_nColumnMax); } return pFiler->filerStatus(); } Acad::ErrorStatus GridRange::dwgOutFields(AcDbDwgFiler* pFiler) const { VERIFY(GridCell::dwgOutFields(pFiler) == Acad::eOk); //VERIFY(m_gridStyle.dwgOutFields(pFiler)==Acad::eOk); //pFiler->writeString(m_sText); //if (g_nSaveTArchVer == 5) { // ASSERT(m_nRowMax <= 256 && m_nColumnMax <= 256); // pFiler->writeItem((Adesk::UInt8)1); // pFiler->writeItem((Adesk::UInt8)m_nRow); // pFiler->writeItem((Adesk::UInt8)m_nColumn); // pFiler->writeItem((Adesk::UInt8)m_nRowMax); // pFiler->writeItem((Adesk::UInt8)m_nColumnMax); //} //else { pFiler->writeItem(g_nVersion); pFiler->writeItem(m_nRow); pFiler->writeItem(m_nColumn); pFiler->writeItem(m_nRowMax); pFiler->writeItem(m_nColumnMax); //} return pFiler->filerStatus(); } /* const TCHAR *GridRange::GetText() const { return (const TCHAR *)m_sText; } */ int GridRange::GetCoord(BOOL bIsRow) const { return (bIsRow ? m_nRow : m_nColumn); } int GridRange::GetCoordMax(BOOL bIsRow) const { return (bIsRow ? m_nRowMax : m_nColumnMax); } /* void GridRange::SetText(const TCHAR *szText) { m_sText=szText; } */ void GridRange::SetCoord(int nRow, int nCol) { m_nRow = nRow; m_nColumn = nCol; } void GridRange::SetCoordMax(int nRow, int nCol) { m_nRowMax = nRow; m_nColumnMax = nCol; } BOOL GridRange::Include(int nRow, int nCol) const { BOOL bRet = (nRow >= m_nRow && nRow <= m_nRowMax && nCol >= m_nColumn && nCol <= m_nColumnMax); return bRet; } //////////////////////////////////// // 标题的定义 const Adesk::UInt8 SheetTitle::g_nVersion = 1; SheetTitle::SheetTitle() { //XString m_sText; m_gridStyle.SetFlagBit(OF_HORMODE | OF_TEXTHEIGHT, TRUE); m_gridStyle.SetHorMode(AcDb::kTextCenter); SetVerMode(AcDb::kTextVertMid); m_bVisibility = TRUE; //m_gridStyle.m_nOverride=0; } SheetTitle::SheetTitle(const SheetTitle &src) { *this = src; } SheetTitle & SheetTitle::operator = (const SheetTitle &src) { GlobalFunc::CopyObject(src, *this); return *this; } BOOL SheetTitle::IsVisible() const { return (m_bVisibility != 0); } void SheetTitle::SetVisible(BOOL bTrue) { m_bVisibility = bTrue; } Acad::ErrorStatus SheetTitle::dwgInFields(AcDbDwgFiler* pFiler) { Acad::ErrorStatus es = SheetRow::dwgInFields(pFiler); if (es != Acad::eOk) return es; es = GridCell::dwgInFields(pFiler); if (es != Acad::eOk) return es; Adesk::UInt8 nVer = 0; pFiler->readItem(&nVer); if (nVer > g_nVersion) // Version is too new return Acad::eMakeMeProxy; //VERIFY(m_gridStyle.dwgInFields(pFiler)==Acad::eOk); //ReadString(pFiler, m_sText); pFiler->readItem(&m_bVisibility); return pFiler->filerStatus(); } Acad::ErrorStatus SheetTitle::dwgOutFields(AcDbDwgFiler* pFiler) const { VERIFY(SheetRow::dwgOutFields(pFiler) == Acad::eOk); VERIFY(GridCell::dwgOutFields(pFiler) == Acad::eOk); pFiler->writeItem(g_nVersion); //VERIFY(m_gridStyle.dwgOutFields(pFiler)==Acad::eOk); //pFiler->writeString(m_sText); pFiler->writeItem(m_bVisibility); return pFiler->filerStatus(); } ///////////////////////////////////////////////////////////// // 表格对象类 ///////////////////////////////////////////////////////////// // TArch5, T6Bet2:ver=2;T6B3:nVer=3, nVer=4 const Adesk::UInt8 CDbSheet::g_nVersion = 4; ACRX_DXF_DEFINE_MEMBERS(CDbSheet, AecXDbEntityBaseEx, AcDb::kDHL_CURRENT, AcDb::kMReleaseCurrent, 1, AEC_ZT_SHEET, "AEC_SHEET图形无法解析, 请下载上华软件|网址: www.shanghuasoft.com"); CDbSheet::CDbSheet() { m_rowHeightStyle = SheetRow::kFixed; m_gridStyle.SetOverrideAll(TRUE); //标准方格样式 m_border.m_nFlag = DividerStyle::kLocal; //表格外框的分割线样式 m_rowDivider.m_nFlag = DividerStyle::kLocal; //表格内部分割线样式 m_colDivider.m_nFlag = DividerStyle::kLocal; //SheetTitle m_title; //标题 //DList m_columns; //列 //DList m_rows; //行 //DList m_ranges; //单元格 m_pCells = NULL; m_nRowHeight = 0.0; //标准行高 //表格本身的定位方式, 左上, 右上, 左下, 右下, 中间 m_nAlignment = AcGiDraw::kTopLeft; //XPoint m_ptLocation; //定位点 m_nRotation = 0.0; } CDbSheet::~CDbSheet() { if (m_pCells) delete[] m_pCells; } void CDbSheet::InitSheet(int nRow, int nCol, double nRowHeight, double nColWidth) { ASSERT(nRow > 0 && nCol > 0); if (m_pCells) delete[] m_pCells; m_pCells = new GridCell[nRow * nCol]; m_columns.Reset(); m_rows.Reset(); m_ranges.Reset(); m_nRowHeight = nRowHeight; for (int i = 0; i < nCol; i++) { SheetColumn *pCol = new SheetColumn; pCol->SetWidth(nColWidth); pCol->SetGridStyle(m_gridStyle); //pCol->SeDividerStyle(m_colDivider); m_columns.Append(pCol); } for (i = 0; i < nRow; i++) { SheetRow *pRow = new SheetRow; pRow->SetHeight(nRowHeight); pRow->SetVerMode(m_gridStyle.GetVerMode()); //pRow->SeDividerStyle(m_rowDivider); m_rows.Append(pRow); } } BOOL CDbSheet::IsValid() const { return (m_nRowHeight > 0.0 && m_rows.Length() && m_columns.Length()); } // 提供对格式刷的支持 void CDbSheet::CopyPropertiesFrom(AcDbEntity *pSrcEntity, unsigned gMatchFlag) { assertWriteEnabled(); AecXDbEntityBaseEx::CopyPropertiesFrom(pSrcEntity, gMatchFlag); CDbSheet *pSrc = CDbSheet::cast(pSrcEntity); if (pSrc) { m_gridStyle = pSrc->m_gridStyle; //标准方格样式 m_border = pSrc->m_border; //表格外框的分割线样式 m_rowDivider = pSrc->m_rowDivider; //行分割线样式 m_colDivider = pSrc->m_colDivider; //列分割线样式 m_nRowHeight = pSrc->m_nRowHeight; //标准行高 //表格本身的定位方式, 左上, 右上, 左下, 右下, 中间 m_nAlignment = pSrc->m_nAlignment; // TArch6 m_rowHeightStyle = pSrc->m_rowHeightStyle; } } // 从DWG读入数据: Acad::ErrorStatus CDbSheet::dwgInFields(AcDbDwgFiler* pFiler) { assertWriteEnabled(); Acad::ErrorStatus es = AecXDbEntityBaseEx::dwgInFields(pFiler); if (es != Acad::eOk) return es; Adesk::UInt8 nVer; pFiler->readItem(&nVer); if (nVer > g_nVersion) {// Version is too new return Acad::eMakeMeProxy; } es = m_gridStyle.dwgInFields(pFiler); if (es != Acad::eOk) return es; es = m_border.dwgInFields(pFiler); if (es != Acad::eOk) return es; es = m_rowDivider.dwgInFields(pFiler); if (es != Acad::eOk) return es; if (nVer > 1) { es = m_colDivider.dwgInFields(pFiler); if (es != Acad::eOk) return es; } es = m_title.dwgInFields(pFiler); if (es != Acad::eOk) return es; Adesk::UInt16 nColNum = 0; m_columns.Reset(); if (nVer > 2) { pFiler->readItem(&nColNum); } else { Adesk::UInt8 nTemp = 0; pFiler->readItem(&nTemp); nColNum = nTemp; } for (Adesk::UInt16 iCol = 0; iCol < nColNum; iCol++) { SheetColumn *pCol = new SheetColumn; es = pCol->dwgInFields(pFiler); if (es != Acad::eOk) { delete pCol; return es; } m_columns.Append(pCol); } m_rows.Reset(); Adesk::UInt16 nRowNum = 0; if (nVer > 2) { pFiler->readItem(&nRowNum); } else { Adesk::UInt8 nTemp = 0; pFiler->readItem(&nTemp); nRowNum = nTemp; } for (Adesk::UInt16 iRow = 0; iRow < nRowNum; iRow++) { SheetRow *pRow = new SheetRow; es = pRow->dwgInFields(pFiler); if (es != Acad::eOk) { delete pRow; return es; } m_rows.Append(pRow); } // 合并格 m_ranges.Reset(); Adesk::UInt16 nRangeNum; pFiler->readItem(&nRangeNum); for (Adesk::UInt16 iRange = 0; iRange < nRangeNum; iRange++) { GridRange *pRange = new GridRange; es = pRange->dwgInFields(pFiler); if (es != Acad::eOk) { delete pRange; return es; } m_ranges.Append(pRange); } //单元格 if (m_pCells) delete[] m_pCells; ASSERT(nRowNum > 0 && nColNum > 0); Adesk::UInt16 nCellNum = nRowNum * nColNum; m_pCells = new GridCell[nCellNum]; for (Adesk::UInt16 iCell = 0; iCell < nCellNum; iCell++) { es = m_pCells[iCell].dwgInFields(pFiler, &m_ranges); if (es != Acad::eOk) return es; } pFiler->readItem(&m_nRowHeight); Adesk::UInt8 nAlign; pFiler->readItem(&nAlign); m_nAlignment = (AcGiDraw::TextAlignment)nAlign; pFiler->readItem((AcGePoint3d *)&m_ptLocation); m_ptLocation.z = 0; pFiler->readItem(&m_nRotation); if (nVer >= 4) { Adesk::UInt8 nTemp; pFiler->readItem(&nTemp); m_rowHeightStyle = (SheetRow::TRowHeightStyle)nTemp; } return pFiler->filerStatus(); } Acad::ErrorStatus CDbSheet::dwgOutFields(AcDbDwgFiler* pFiler) const { assertReadEnabled(); Acad::ErrorStatus es = AecXDbEntityBaseEx::dwgOutFields(pFiler); if (es != Acad::eOk) return es; //if (g_nSaveTArchVer == 5) // pFiler->writeItem((Adesk::UInt8)2); //else pFiler->writeItem(g_nVersion); VERIFY(m_gridStyle.dwgOutFields(pFiler) == Acad::eOk); VERIFY(m_border.dwgOutFields(pFiler) == Acad::eOk); VERIFY(m_rowDivider.dwgOutFields(pFiler) == Acad::eOk); VERIFY(m_colDivider.dwgOutFields(pFiler) == Acad::eOk); VERIFY(m_title.dwgOutFields(pFiler) == Acad::eOk); Adesk::UInt16 nColNum = m_columns.Length(); //if (g_nSaveTArchVer == 5) { // ASSERT(nColNum <= 256); // pFiler->writeItem((Adesk::UInt8)nColNum); //} //else pFiler->writeItem(nColNum); for (Adesk::UInt16 iCol = 0; iCol < nColNum; iCol++) { VERIFY(m_columns[iCol].dwgOutFields(pFiler) == Acad::eOk); } Adesk::UInt16 nRowNum = m_rows.Length(); //if (g_nSaveTArchVer == 5) { // ASSERT(nRowNum <= 256); // pFiler->writeItem((Adesk::UInt8)nRowNum); //} //else pFiler->writeItem(nRowNum); for (Adesk::UInt16 iRow = 0; iRow < nRowNum; iRow++) { VERIFY(m_rows[iRow].dwgOutFields(pFiler) == Acad::eOk); } Adesk::UInt16 nRangeNum = m_ranges.Length(); pFiler->writeItem(nRangeNum); for (Adesk::UInt16 iRange = 0; iRange < nRangeNum; iRange++) { VERIFY(m_ranges[iRange].dwgOutFields(pFiler) == Acad::eOk); } Adesk::UInt16 nCellNum = nRowNum * nColNum; for (Adesk::UInt16 iCell = 0; iCell < nCellNum; iCell++) { VERIFY(m_pCells[iCell].dwgOutFields(pFiler, &m_ranges) == Acad::eOk); } pFiler->writeItem(m_nRowHeight); pFiler->writeItem((Adesk::UInt8)m_nAlignment); pFiler->writeItem((const AcGePoint3d &)m_ptLocation); pFiler->writeItem(m_nRotation); //if (g_nSaveTArchVer != 5) { pFiler->writeItem((Adesk::UInt8)m_rowHeightStyle); //} return pFiler->filerStatus(); } Acad::ErrorStatus CDbSheet::dxfInFields(AcDbDxfFiler* pFiler) { assertWriteEnabled(); Acad::ErrorStatus es = AecXDbEntityBaseEx::dxfInFields(pFiler); if (es != Acad::eOk) return es; if (!pFiler->atSubclassData(_T("CDbSheet"))) { return Acad::eBadDxfSequence; } pFiler->writePoint2d(AcDb::kDxfXCoord, m_ptLocation.AsAcGePoint2d()); pFiler->writeString(AcDb::kDxfText, (const TCHAR *)GetTitleText()); pFiler->writeDouble(AcDb::kDxfReal, m_nRowHeight); pFiler->writeDouble(AcDb::kDxfAngle, m_nRotation); pFiler->writeInt16(AcDb::kDxfInt16, (Adesk::Int16)GetRowNum()); pFiler->writeInt16(AcDb::kDxfInt16 + 1, (Adesk::Int16)GetColumnNum()); pFiler->writeInt16(AcDb::kDxfInt16 + 2, (Adesk::Int16)m_nAlignment); int fieldsFlags = 0; XPoint pt; XString sText; double nHeight, nRot; int nAlign; resbuf rb; while ((es == Acad::eOk) && ((es = pFiler->readResBuf(&rb)) == Acad::eOk)) { switch (rb.restype) { case AcDb::kDxfXCoord: pt = rb.resval.rpoint; fieldsFlags |= 0x01; break; case AcDb::kDxfText: sText = rb.resval.rstring; fieldsFlags |= 0x02; break; case AcDb::kDxfReal: nHeight = rb.resval.rreal; fieldsFlags |= 0x04; break; case AcDb::kDxfAngle: nRot = rb.resval.rreal; fieldsFlags |= 0x08; break; case AcDb::kDxfInt16: fieldsFlags |= 0x10; break; case AcDb::kDxfInt16 + 1: fieldsFlags |= 0x20; break; case AcDb::kDxfInt16 + 2: fieldsFlags |= 0x40; nAlign = rb.resval.rint; break; //fall through intentional default: // An unrecognized group. Push it back so that // the subclass can read it again. pFiler->pushBackItem(); es = Acad::eEndOfFile; break; } } if (es != Acad::eEndOfFile) return Acad::eInvalidResBuf; if (fieldsFlags & 0x01) m_ptLocation = pt; if (fieldsFlags & 0x02) SetTitleText(sText); if (fieldsFlags & 0x04) m_nRowHeight = nHeight; if (fieldsFlags & 0x08) m_nRotation = nRot; if (fieldsFlags & 0x40) m_nAlignment = (AcGiDraw::TextAlignment)nAlign; return pFiler->filerStatus(); } Acad::ErrorStatus CDbSheet::dxfOutFields(AcDbDxfFiler* pFiler) const { assertReadEnabled(); Acad::ErrorStatus es = AecXDbEntityBaseEx::dxfOutFields(pFiler); assert(es == Acad::eOk); es = pFiler->writeItem(AcDb::kDxfSubclass, _T("CDbSheet")); assert(es == Acad::eOk); pFiler->writePoint2d(AcDb::kDxfXCoord, m_ptLocation.AsAcGePoint2d()); pFiler->writeString(AcDb::kDxfText, (const TCHAR *)GetTitleText()); pFiler->writeDouble(AcDb::kDxfReal, m_nRowHeight); pFiler->writeDouble(AcDb::kDxfAngle, m_nRotation); pFiler->writeInt16(AcDb::kDxfInt16, (Adesk::Int16)GetRowNum()); pFiler->writeInt16(AcDb::kDxfInt16 + 1, (Adesk::Int16)GetColumnNum()); pFiler->writeInt16(AcDb::kDxfInt16 + 2, (Adesk::Int16)m_nAlignment); return es; } // ----------------------------------------------------------------------- // Overriden functions for edit // to do: // 允许通过夹点改变边界 Acad::ErrorStatus CDbSheet::subGetGripPoints(AcGePoint3dArray& gripPoints, AcDbIntArray& osnapModes, AcDbIntArray& geomIds) const { assertReadEnabled(); gripPoints.append(m_ptLocation); //0 XPoint ptTopLeft = GetTopLeft(FALSE); XPoint ext = GetExtents(FALSE, FALSE); XPoint ptBotRight; double nRotWcs = Layout2Wcs(m_nRotation); ads_polar(ptTopLeft, nRotWcs - PI / 2, ext.y, ptBotRight); ads_polar(XPoint(ptBotRight), nRotWcs, ext.x, ptBotRight); gripPoints.append(ptBotRight); //1 int nColNum = GetColumnNum(); for (int iCol = 0; iCol < nColNum; iCol++) { const SheetColumn &column = m_columns[iCol]; if (column.AllowSizing()) { double nWidth = GetColumnsWidth(0, iCol, FALSE); XPoint pt; ads_polar(ptTopLeft, nRotWcs, nWidth, pt); gripPoints.append(pt); } } int nRowNum = GetRowNum(); for (int iRow = 0; iRow < nRowNum; iRow++) { const SheetRow &row = m_rows[iRow]; if (row.GetRowHeightStyle() == SheetRow::kFree || row.GetRowHeightStyle() == SheetRow::kAtLeast || (row.GetRowHeightStyle() == SheetRow::kParent && (m_rowHeightStyle == SheetRow::kFree || m_rowHeightStyle == SheetRow::kAtLeast)) ) { double nHeight = GetRowsHeight(0, iRow, FALSE); XPoint pt; ads_polar(ptTopLeft, nRotWcs - PI / 2, nHeight, pt); gripPoints.append(pt); } } return Acad::eOk; } // stretch points is diffrent from grep points, with no midpoint included Acad::ErrorStatus CDbSheet::subGetStretchPoints(AcGePoint3dArray & stretchPoints) const { assertReadEnabled(); AcDbIntArray osnapModes; AcDbIntArray geomIds; return subGetGripPoints(stretchPoints, osnapModes, geomIds); } // Active when being rotated, scaled, moved, etc. // Scale is disabled here Acad::ErrorStatus CDbSheet::subTransformBy(const AcGeMatrix3d& xform) { assertWriteEnabled(); AcDbEntity::subTransformBy(xform); ads_matrix mat; GlobalFunc::AsAdsMatrix(xform, mat); if (!g_Option::instance().g_bLayoutRotate) { AcGeVector3d vt(cos(m_nRotation), sin(m_nRotation), 0.0); vt.transformBy(xform); m_nRotation = ads_angle(XPoint(), XPoint(vt[0], vt[1])); } m_ptLocation.TransformBy(mat); return Acad::eOk; } // 功能: 夹点操作 Acad::ErrorStatus CDbSheet::subMoveGripPointsAt( const AcDbIntArray& indices, const AcGeVector3d& offset) { assertWriteEnabled(); XPoint vtOffset(offset[0], offset[1]); if (indices.length() > 1) { m_ptLocation += vtOffset; return Acad::eOk; } double nRotWcs = Layout2Wcs(m_nRotation); int idx = indices[0]; if (idx == 0) { m_ptLocation += vtOffset; } else if (idx == 1) { XVector3D vtRight(cos(nRotWcs), sin(nRotWcs)); XVector3D vtBot(cos(nRotWcs - PI / 2), sin(nRotWcs - PI / 2)); //double nWidthInc = (vtRight & vtOffset); //double nHeightInc = (vtBot & vtOffset); double nWidthInc = GlobalFunc::operator&(vtRight, vtOffset); double nHeightInc = GlobalFunc::operator&(vtBot, vtOffset); BOOL bIncTitle = m_title.IsVisible(); XPoint ptTopLeft = GetTopLeft(bIncTitle); XPoint ext = GetExtents(bIncTitle, FALSE); double xRatio = nWidthInc / ext.x + 1.0; double yRatio = nHeightInc / ext.y + 1.0; int nColNum = GetColumnNum(); for (int iCol = 0; iCol < nColNum; iCol++) { SheetColumn &column = *m_columns[iCol]; column.m_nWidth *= xRatio; column.m_gridStyle.m_nTextHeight *= yRatio; } m_gridStyle.m_nTextHeight *= yRatio; int nRowNum = GetRowNum(); for (int iRow = 0; iRow < nRowNum; iRow++) { SheetRow &row = *m_rows[iRow]; row.m_nHeight *= yRatio; for (iCol = 0; iCol < nColNum; iCol++) { GridCell *pCell = (*this)(iRow, iCol); //GridStyle gridStyle; //GlobalFunc::CopyObject(pCell->GetGridStyle(), gridStyle); pCell->m_gridStyle.m_nTextHeight *= yRatio; //pCell->SetGridStyle(gridStyle); } } for (int n = 0; n < m_ranges.Length(); n++) m_ranges[n]->m_gridStyle.m_nTextHeight *= yRatio; m_nRowHeight *= yRatio; m_title.m_nHeight *= yRatio; m_title.m_gridStyle.m_nTextHeight *= yRatio; } else { XVector3D vt(cos(nRotWcs), sin(nRotWcs)); //double nWidth = (vt & vtOffset); double nWidth = GlobalFunc::operator&(vt, vtOffset); int nColNum = GetColumnNum(); int iVert = 1; for (int iCol = 0; iCol < nColNum; iCol++) { SheetColumn &column = *m_columns[iCol]; if (column.AllowSizing()) { iVert++; if (idx == iVert) { if (column.GetWidth() * GetPScale() + nWidth < g_Option::instance()._DIST_SNAP) { //Delete column RemoveColumn(iCol); } else { column.SetWidth(column.GetWidth() + nWidth / GetPScale()); CalculateRowHeight(0, GetRowNum() - 1); } return Acad::eOk; } } } XVector3D vt1(cos(nRotWcs - PI / 2), sin(nRotWcs - PI / 2)); //double nHeight = (vt1 & vtOffset); double nHeight = GlobalFunc::operator&(vt1, vtOffset); int nRowNum = GetRowNum(); for (int iRow = 0; iRow < nRowNum; iRow++) { SheetRow &row = *m_rows[iRow]; if (row.GetRowHeightStyle() == SheetRow::kFree || row.GetRowHeightStyle() == SheetRow::kAtLeast || (row.GetRowHeightStyle() == SheetRow::kParent && (m_rowHeightStyle == SheetRow::kFree || m_rowHeightStyle == SheetRow::kAtLeast)) ) { iVert++; if (idx == iVert) { if (row.GetHeight() * GetPScale() + nHeight < g_Option::instance()._DIST_SNAP) RemoveRow(iRow); else { double h = row.GetHeight() + nHeight / GetPScale(); if (row.GetRowHeightStyle() == SheetRow::kAtLeast || (row.GetRowHeightStyle() == SheetRow::kParent && m_rowHeightStyle == SheetRow::kAtLeast) ) { if (h > GetRowHeight(TRUE)) row.SetHeight(h); else row.SetHeight(GetRowHeight(TRUE)); } else row.SetHeight(h); } return Acad::eOk; } } } } return Acad::eOk; } // 功能: 夹点操作 Acad::ErrorStatus CDbSheet::subMoveStretchPointsAt( const AcDbIntArray& indices, const AcGeVector3d& offset) { return subMoveGripPointsAt(indices, offset); } // 取得夹点说明 Acad::ErrorStatus CDbSheet::GetGripText(int i, CString &cs) const { Acad::ErrorStatus es = Acad::eOk; if (i == 0) { cs = _T("移动表格"); } else if (i == 1) { cs = _T("角点缩放"); } else { int nColNum = GetColumnNum(); int iVert = 1; for (int iCol = 0; iCol < nColNum; iCol++) { const SheetColumn &column = m_columns[iCol]; if (column.AllowSizing()) { iVert++; if (i == iVert) { cs.Format(_T("移动第%d列"), iCol + 1); return Acad::eOk; } } } int nRowNum = GetRowNum(); for (int iRow = 0; iRow < nRowNum; iRow++) { const SheetRow &row = m_rows[iRow]; if (row.GetRowHeightStyle() == SheetRow::kFree || row.GetRowHeightStyle() == SheetRow::kAtLeast || (row.GetRowHeightStyle() == SheetRow::kParent && (m_rowHeightStyle == SheetRow::kFree || m_rowHeightStyle == SheetRow::kAtLeast)) ) { iVert++; if (i == iVert) { cs.Format(_T("移动第%d行"), iRow + 1); if (row.GetRowHeightStyle() == SheetRow::kFree || (row.GetRowHeightStyle() == SheetRow::kParent && m_rowHeightStyle == SheetRow::kFree) ) cs += _T("(自由移动)"); else cs += _T("(不小于表格行高)"); return Acad::eOk; } } } } return es; } DrawModeType CDbSheet::GetDrawType() const { return k2DOnly; } int CDbSheet::ConvertText(TConvertTextPtr ptr, void *pData) { assertWriteEnabled(); int nRow = GetRowNum(); int nCol = GetColumnNum(); int nCode = RTNONE; XString sText; nCode = ptr(m_title.m_sText, sText, pData); if (nCode == RTNORM) m_title.m_sText = sText; for (int iRow = 0; iRow < nRow; iRow++) { for (int iCol = 0; iCol < nCol; iCol++) { GridCell &cell = m_pCells[iRow * nCol + iCol]; int nRet = ptr(cell.m_sText, sText, pData); if (nRet == RTERROR) nCode = nRet; else if (nRet == RTNORM) cell.m_sText = sText; } } for (int i = 0; i < m_ranges.Length(); i++) { GridRange *cell = m_ranges[i]; int nRet = ptr(cell->m_sText, sText, pData); if (nRet == RTERROR) nCode = nRet; else if (nRet == RTNORM) cell->m_sText = sText; } return nCode; } // 返回发现的位置,同时posStart往前移动(以便继续找下一个使用), TextPosition CDbSheet::FindSubText(const TCHAR *sSubText, TextPosition &posStart, TextRange *pRange) const { TextPosition pos; if (!sSubText || !sSubText[0]) return pos; TextPosition posNext = posStart; while (1) { if ((int)posNext.m_nCookies >= (GetRowNum() * GetColumnNum() + m_ranges.Length() + 1)) break; AecXDbText *pText = GetText(posNext.m_nCookies); TextPosition posFind; if (pText) { posFind = pText->FindSubText(sSubText, posNext, pRange); delete pText; } if (!posFind) { posNext.m_nCookies++; posNext.m_nTextPos = 0; } else { posStart = posNext; if (!posStart) { posStart.m_nCookies++; posStart.m_nTextPos = 0; } posFind.m_nCookies = posNext.m_nCookies; pos = posFind; break; } } return pos; } // 返回下一次查找的开始位置 TextPosition CDbSheet::ReplaceSubText(const TextPosition &posRep, const TCHAR *sRepText, TextRange *pRange) { assertWriteEnabled(); TextPosition posNext; AecXDbText *pText = GetText(posRep.m_nCookies); if (!pText) return posNext; posNext = pText->ReplaceSubText(posRep, sRepText, pRange); int cookies = posRep.m_nCookies; if (cookies == 0) { SetTitleText(pText->GetText()); } else { cookies--; int nRowNum = GetRowNum(); int nColNum = GetColumnNum(); if (cookies < nRowNum * nColNum) { int nRow = cookies / nColNum; int nCol = cookies - nRow * nColNum; GridCell *cell = (*this)(nRow, nCol); cell->SetText(pText->GetText()); } else { cookies -= nRowNum * nColNum; if (cookies < m_ranges.Length()) m_ranges[cookies]->SetText(pText->GetText()); } } delete pText; if (!posNext) { posNext.m_nCookies = posRep.m_nCookies + 1; posNext.m_nTextPos = 0; } return posNext; } /* * * * * * * * * * 取 动 态 属 性 显 示 数 据 的 函 数 * * * * * * * * * */ void CDbSheet::GetTips(DList &lstInfo) const { lstInfo.Append(new ObjInfoUnit(_T("对象类型"), _T("表格"))); const TCHAR *pszTitle = m_title.IsVisible() ? _T("标题") : _T("标题(隐藏)"); lstInfo.Append(new ObjInfoUnit(pszTitle, m_title.GetText())); XPoint ext = GetExtents(m_title.IsVisible() && m_title.GetDividerStyle().GetDividerFlag() != DividerStyle::kNone); XString sHeight, sWidth, sRowHeight; GlobalFunc::ftoa(ext.x, 1, sWidth); GlobalFunc::ftoa(ext.y, 1, sHeight); GlobalFunc::ftoa(GetRowHeight(), 1, sRowHeight); sHeight << _T("P"); sWidth << _T("P"); sRowHeight << _T("P"); lstInfo.Append(new ObjInfoUnit(_T("标准行高"), sRowHeight)); lstInfo.Append(new ObjInfoUnit(_T("表格宽度"), sWidth)); lstInfo.Append(new ObjInfoUnit(_T("表格高度"), sHeight)); lstInfo.Append(new ObjInfoUnit(_T("行数"), XString(_T("%d"), GetRowNum()))); lstInfo.Append(new ObjInfoUnit(_T("列数"), XString(_T("%d"), GetColumnNum()))); } Acad::ErrorStatus CDbSheet::Draw2d(AcGiDraw &dc) const { //TPushProperty vProp(this, dc); //add on 20161017 图层关闭,不进行相关绘制,解决表格对象内有图块,当表格图层关闭,打印显示图块的问题。 AcDbLayerTableRecordPointer player(this->layerId(), AcDb::kForRead); if (player.openStatus() == Acad::eOk && player->isOff())//对图层为空时,进行保护 { return Acad::eOk; } //end add assertReadEnabled(); int nGsMarker = 1; //if (!objectId() && _tcsicmp(dc.Desc(), AcGiViewDraw::Descriptor()) == 0) if (!objectId() && dc.GetCommonDraw()) nGsMarker = 0; DrawBorder(dc, nGsMarker); DrawTitle(dc, nGsMarker); XPoint ptBase = GetTopLeft(FALSE); DrawRowDivider(ptBase, dc, nGsMarker); DrawColumnDivider(ptBase, dc, nGsMarker); if (!!objectId()) DrawCellText(ptBase, dc, nGsMarker); return Acad::eOk; } //////////////////////////////////////////////////////////////////// // 绘制表格的方法 // 绘制表格的外框 void CDbSheet::DrawBorder(AcGiDraw &dc, int &nGsMarker) const { AcDbPolyline pline; XPoly2D polyBorder(1); GetBorder(polyBorder); GlobalFunc::PolyConvert(polyBorder, pline); pline.setPropertiesFrom(this); if (nGsMarker) { dc.SetSelectionMarker(nGsMarker); nGsMarker++; //捕捉加速 //INT_PTR nQuickMarker = GetQuickMarker(); //if (nQuickMarker && nQuickMarker < (nGsMarker - 4) || nQuickMarker >= nGsMarker) //用于捕捉时加速 // return; } int nOldColor = dc.GetColor(); switch (m_border.m_nFlag) { case DividerStyle::kLocal: if (!!m_border.m_idLineType) pline.setLinetype(m_border.m_idLineType); if (m_border.m_nLineWidth > 0.0 && !!objectId()) pline.setConstantWidth(m_border.m_nLineWidth * GetPScale()); if (m_border.m_nColor > 0) { dc.SetColor(m_border.GetColor()); pline.setColorIndex(m_border.GetColor()); } //dc.Polyline(pline); DrawPline(dc, pline); break; case DividerStyle::kParent: //dc.Polyline(pline); DrawPline(dc, pline); break; case DividerStyle::kNone: default: break; } dc.SetColor(nOldColor); } // 当Wrap和一行容纳不下时采用MText void CDbSheet::InitTextInBox(AecXDbText &text, XPoint ptTopLeft, double nBoxWidth, double nBoxHeight, double nOffset, AcDb::TextHorzMode nHorMode, AcDb::TextVertMode nVerMode) const { BOOL bMText = text.isKindOf(AecXDbMText::desc()); XPoint ptAlign = ptTopLeft; if (!bMText) { AcGiDraw::TextAlignment align = GlobalFunc::GetTextAlignment(nHorMode, nVerMode); switch (nHorMode) { case AcDb::kTextLeft: ptAlign.x += nOffset; break; case AcDb::kTextCenter: case AcDb::kTextMid: ptAlign.x += nBoxWidth / 2; break; case AcDb::kTextRight: ptAlign.x += nBoxWidth; ptAlign.x -= nOffset; break; default: ptAlign.x += nOffset; break; } switch (nVerMode) { case AcDb::kTextBase: case AcDb::kTextBottom: ptAlign.y -= nBoxHeight; ptAlign.y += nOffset; if (align == AcGiDraw::kTextFit || align == AcGiDraw::kUnknown) align = AcGiDraw::kLeft; break; case AcDb::kTextVertMid: ptAlign.y -= nBoxHeight / 2; if (align == AcGiDraw::kTextFit || align == AcGiDraw::kUnknown) align = AcGiDraw::kMiddleLeft; break; case AcDb::kTextTop: ptAlign.y -= nOffset; if (align == AcGiDraw::kTextFit || align == AcGiDraw::kUnknown) align = AcGiDraw::kTopLeft; break; default: ASSERT(0); } text.SetAlignment(align); text.SetLocation(ptAlign); } else { AcGiDraw::TextAlignment align; ptAlign.x += nOffset; switch (nHorMode) { case AcDb::kTextLeft: align = AcGiDraw::kLeft; break; case AcDb::kTextCenter: case AcDb::kTextMid: align = AcGiDraw::kCenter; break; case AcDb::kTextRight: align = AcGiDraw::kRight; break; case AcDb::kTextFit: align = AcGiDraw::kTextFit; break; default: ASSERT(0); } text.SetAlignment(align); XPoint ext = text.GetExtents(); switch (nVerMode) { case AcDb::kTextBase: case AcDb::kTextBottom: ptAlign.y -= nBoxHeight; ptAlign.y += nOffset + ext.y; break; case AcDb::kTextVertMid: ptAlign.y -= nBoxHeight / 2; ptAlign.y += ext.y / 2; break; case AcDb::kTextTop: ptAlign.y -= nOffset; break; default: ASSERT(0); } text.SetLocation(ptAlign); } } // 绘制标题, 包括文字和横线 // ptBase -- 标题上(IN)下(OUT)的第一左上角 void CDbSheet::DrawTitle(AcGiDraw &dc, int &nGsMarker) const { if (!m_title.IsVisible()) return; BOOL bIncludeTitle = (m_title.m_divider.m_nFlag != DividerStyle::kNone); double nTitleHeight = GetTitleHeight(FALSE); double nTitleWidth = GetSheetWidth(FALSE); double nRotWcs = Layout2Wcs(m_nRotation); //左上角为ptBase XPoint ptBase = GetTopLeft(bIncludeTitle); if (!bIncludeTitle) ads_polar(XPoint(ptBase), nRotWcs + PI / 2, nTitleHeight, ptBase); //INT_PTR nQuickMarker = GetQuickMarker(); BOOL bDrawText = TRUE; if (nGsMarker) { dc.SetSelectionMarker(nGsMarker); nGsMarker++; //捕捉时加速 //if (nQuickMarker && (nGsMarker - 1) != nQuickMarker) // bDrawText = FALSE; //else bDrawText = TRUE; } else { bDrawText = FALSE; } ads_matrix mat; ptBase.GetRotationMatrix(nRotWcs, mat); if (bDrawText && !!m_title.m_sText) { //绘制文字 double nOffset = GetTitleLineSpace(FALSE); double nTextHeight = GetTitleTextHeight(TRUE); AcDbObjectId idTextStyle = GetTitleTextStyle(); AecXDbText textLine; textLine.setPropertiesFrom(this); textLine.SetHeight(nTextHeight); textLine.SetStyleId(idTextStyle); textLine.SetText(m_title.m_sText); const TCHAR *bHardMText = _tcschr(m_title.GetText(), _T('\n')); AecXDbText *pDbText = NULL; if (bHardMText || (textLine.GetExtents().x + nOffset * 2 > nTitleWidth && IsTitleWrapEnabled()) ) { AecXDbMText *pTextSeg = new AecXDbMText; pDbText = pTextSeg; pDbText->setPropertiesFrom(this); AecXDbMText &textSeg = *pTextSeg; textSeg.SetLineSpace(nOffset, FALSE); textSeg.SetPageWidth(nTitleWidth - 2 * nOffset, FALSE); } else { pDbText = new AecXDbText; pDbText->setPropertiesFrom(this); } Adesk::UInt16 nColor = GetTitleTextColor(); int nOldColor = dc.GetColor(); if (nColor > 0) { pDbText->setColorIndex(nColor); dc.SetColor(nColor); } pDbText->SetHeight(nTextHeight); pDbText->SetStyleId(idTextStyle); pDbText->SetText(m_title.m_sText); InitTextInBox(*pDbText, ptBase, nTitleWidth, nTitleHeight, nOffset, GetTitleHorMode(), GetTitleVerMode()); XPoint ptLoc = pDbText->GetLocation(); ptLoc.TransformBy(mat); pDbText->SetLocation(ptLoc); pDbText->SetRotation(m_nRotation); //if (dc.IsFullExplode()) // pDbText->ExplodeOrDraw2d(dc); //else //dc.DrawEntity(*pDbText); DrawBaseEx(dc, *pDbText); delete pDbText; if (nColor > 0) dc.SetColor(nOldColor); } ads_polar(XPoint(ptBase), nRotWcs - PI / 2, nTitleHeight, ptBase); XPoint ptRight; ads_polar(ptBase, nRotWcs, nTitleWidth, ptRight); if (nGsMarker) { dc.SetSelectionMarker(nGsMarker); nGsMarker++; //捕捉加速 //if (nQuickMarker && (nGsMarker - 1) != nQuickMarker) // return; } int nOldColor = dc.GetColor(); AcDbPolyline pline; pline.addVertexAt(0, ptBase); pline.addVertexAt(1, ptRight); pline.setPropertiesFrom(this); const DividerStyle ÷r = m_title.m_divider; switch (divider.m_nFlag) { case DividerStyle::kLocal: case DividerStyle::kParent: if (!!m_title.m_divider.m_idLineType) pline.setLinetype(m_title.m_divider.m_idLineType); if (m_title.m_divider.m_nLineWidth > 0.0 && !!objectId()) pline.setConstantWidth(m_title.m_divider.m_nLineWidth * GetPScale()); if (m_title.m_divider.m_nColor > 0) { dc.SetColor(m_title.m_divider.m_nColor); pline.setColorIndex(m_title.m_divider.m_nColor); } //dc.Polyline(pline); DrawPline(dc, pline); break; case DividerStyle::kNone: default: break; } dc.SetColor(nOldColor); } // 绘制表格的行分割线 void CDbSheet::DrawRowDivider(int nRow, XPoint ptLeft, AcGiDraw &dc) const { AcDbPolyline pline; if (!InitRowDivider(pline, nRow)) return; DList lstSegments; int nColNum = m_columns.Length(); double nScale = GetPScale(); XLine lnSeg; XPoint ptFrom = ptLeft; XPoint ptStart; BOOL bStartValid = FALSE; double nRotWcs = Layout2Wcs(m_nRotation); for (int nCol = 0; nCol < nColNum; nCol++) { const SheetColumn &column = m_columns[nCol]; double nColWidth = column.m_nWidth * nScale; XPoint ptTo; ads_polar(ptFrom, nRotWcs, nColWidth, ptTo); if (HasRowDivider(nRow, nCol)) { if (!bStartValid) { bStartValid = TRUE; ptStart = ptFrom; } if (nCol == nColNum - 1) { lstSegments.Append(new XLine(ptStart, ptTo)); } } else if (bStartValid) { lstSegments.Append(new XLine(ptStart, ptFrom)); bStartValid = FALSE; } ptFrom = ptTo; } for (int i = 0; i < lstSegments.Length(); i++) { XLine *pLine = lstSegments[i]; if (i == 0) { pline.addVertexAt(0, pLine->StartPoint()); pline.addVertexAt(1, pLine->EndPoint()); } else { pline.setPointAt(0, pLine->StartPoint()); pline.setPointAt(1, pLine->EndPoint()); } //dc.Polyline(pline); DrawPline(dc, pline); } } // 绘制行分割线 void CDbSheet::DrawRowDivider(XPoint ptBase, AcGiDraw &dc, int &nGsMarker) const { int nRowNum = m_rows.Length(); XPoint ptLeft = ptBase; //INT_PTR nQuickMarker = GetQuickMarker(); double nRotWcs = Layout2Wcs(m_nRotation); for (int n = 0; n < nRowNum - 1; n++) { ads_polar(XPoint(ptLeft), nRotWcs - PI / 2, GetRowHeight(n, FALSE), ptLeft); if (nGsMarker) { dc.SetSelectionMarker(nGsMarker); nGsMarker++; //捕捉加速 //if (nQuickMarker && (nGsMarker - 1) != nQuickMarker) // continue;//用于捕捉时加速 } DrawRowDivider(n, ptLeft, dc); }; } // 绘制表格列分割线 void CDbSheet::DrawColumnDivider(int nCol, XPoint ptTop, AcGiDraw &dc) const { AcDbPolyline pline; if (!InitColumnDivider(pline, nCol)) return; double nRotWcs = Layout2Wcs(m_nRotation); DList lstSegments; int nRowNum = m_rows.Length(); double nScale = GetPScale(); XLine lnSeg; XPoint ptFrom = ptTop; XPoint ptStart; BOOL bStartValid = FALSE; for (int nRow = 0; nRow < nRowNum; nRow++) { double nRowHeight = GetRowHeight(nRow, FALSE); XPoint ptTo; ads_polar(ptFrom, nRotWcs - PI / 2.0, nRowHeight, ptTo); if (HasColumnDivider(nRow, nCol)) { if (!bStartValid) { bStartValid = TRUE; ptStart = ptFrom; } if (nRow == nRowNum - 1) { lstSegments.Append(new XLine(ptStart, ptTo)); } } else if (bStartValid) { lstSegments.Append(new XLine(ptStart, ptFrom)); bStartValid = FALSE; } ptFrom = ptTo; } for (int i = 0; i < lstSegments.Length(); i++) { XLine *pLine = lstSegments[i]; if (i == 0) { pline.addVertexAt(0, pLine->StartPoint()); pline.addVertexAt(1, pLine->EndPoint()); } else { pline.setPointAt(0, pLine->StartPoint()); pline.setPointAt(1, pLine->EndPoint()); } //dc.Polyline(pline); DrawPline(dc, pline); } } // 绘制表格列分割线 void CDbSheet::DrawColumnDivider(XPoint ptBase, AcGiDraw &dc, int &nGsMarker) const { double nRotWcs = Layout2Wcs(m_nRotation); int nColNum = m_columns.Length(); XPoint ptTop = ptBase; //INT_PTR nQuickMarker = GetQuickMarker(); for (int n = 0; n < nColNum - 1; n++) { ads_polar(XPoint(ptTop), nRotWcs, GetColumnWidth(n, FALSE), ptTop); if (nGsMarker) { dc.SetSelectionMarker(nGsMarker); nGsMarker++; //捕捉加速 //if (nQuickMarker && (nGsMarker - 1) != nQuickMarker) // continue;//用于捕捉时加速 } DrawColumnDivider(n, ptTop, dc); }; } // 绘制单元格的文本 void CDbSheet::DrawRangeText(const GridRange &range, XPoint ptTopLeft, AcGiDraw &dc)const { BOOL bValid = (range.m_nRow >= 0 && range.m_nRow <= range.m_nRowMax && range.m_nColumn >= 0 && range.m_nColumn <= range.m_nColumnMax && range.m_nRowMax < GetRowNum() && range.m_nColumnMax < GetColumnNum()); if (!bValid) return; double x = GetColumnsWidth(0, range.m_nColumn - 1, FALSE); double y = GetRowsHeight(0, range.m_nRow - 1, FALSE); double w, h; w = GetColumnsWidth(range.m_nColumn, range.m_nColumnMax, FALSE); h = GetRowsHeight(range.m_nRow, range.m_nRowMax, FALSE); double nRotWcs = Layout2Wcs(m_nRotation); //左上角为ptBase XPoint ptBase; ads_polar(ptTopLeft, nRotWcs, x, ptBase); ads_polar(XPoint(ptBase), nRotWcs - PI / 2, y, ptBase); DrawCellText(range.GetText(), w, h, range.m_nRow, range.m_nColumn, ptBase, dc); } void CDbSheet::DrawCellText(int nRow, int nCol, XPoint ptTopLeft, AcGiDraw &dc) const { const GridCell &cell = *(*this)(nRow, nCol); if (cell.IsRange()) return; double x = GetColumnsWidth(0, nCol - 1, FALSE); double y = GetRowsHeight(0, nRow - 1, FALSE); double w, h; w = GetColumnWidth(nCol, FALSE); h = GetRowHeight(nRow, FALSE); double nRotWcs = Layout2Wcs(m_nRotation); //左上角为ptBase XPoint ptBase; ads_polar(ptTopLeft, nRotWcs, x, ptBase); ads_polar(XPoint(ptBase), nRotWcs - PI / 2, y, ptBase); DrawCellText(cell.GetText(), w, h, nRow, nCol, ptBase, dc); } // sg add 101116,支持统一标高 bool CDbSheet::UnifyElevation(double dElevation) { assertWriteEnabled(); m_ptLocation.z = dElevation; return true; } int AttribValue::FindByName(const AttribValue *p1, const void *p2) { return _tcsicmp(p1->m_sName, (const TCHAR *)p2); } BOOL CellBlockInsert::OutputDesc(XString &sDescOut) const { if (!m_sBlockName) return FALSE; XString sDesc(2048); sDesc << _T("^B{"); sDesc << _T("BLOCK=") << m_sBlockName << _T(";"); sDesc << _T("FLAG=") << m_nControlFlag << _T(";"); if (!(m_nControlFlag & CBF_AUTOSIZE)) { sDesc << _T("X=") << m_xValue << _T(";") << _T("Y=") << m_yValue << _T(";") << _T("Z=") << m_zValue << _T(";"); } sDesc << _T("}"); if (m_nControlFlag & CBF_SHOW_ATTR) { sDesc << _T("{"); for (int i = 0; i < m_lstAttribs.Length(); i++) { const AttribValue &attr = m_lstAttribs[i]; sDesc << attr.m_sName << _T("=") << attr.m_sValue << _T(";"); } sDesc << _T("}"); } sDescOut = sDesc; return TRUE; } BOOL CellBlockInsert::ParserDesc(const TCHAR *pszText) { if (!pszText) return FALSE; size_t nCharNum = _tcslen(pszText); if (nCharNum > 4 && nCharNum < 2048); else return FALSE; if (pszText[0] == _T('^') && pszText[1] == _T('B') && pszText[2] == _T('{')); else return FALSE; const TCHAR *pEndBlock = _tcschr(pszText, _T('}')); if (!pEndBlock) return FALSE; XString sBlockInfo(2048); GlobalFunc::_StrCpy(sBlockInfo, &pszText[3], pEndBlock); //取图块描述 // 分析图块描述 TCHAR *pBegStat = sBlockInfo; while (pBegStat && *pBegStat) { XString sStatement(2048); TCHAR *pEndStat = _tcschr(pBegStat, _T(';')); if (!pEndStat) break; GlobalFunc::_StrCpy(sStatement, pBegStat, pEndStat); TCHAR *pEqual = _tcschr(sStatement, _T('=')); if (!pEqual) return FALSE; XString sLeftValue(2048), sRightValue(2048); GlobalFunc::_StrCpy(sLeftValue, sStatement, pEqual); GlobalFunc::_StrCpy(sRightValue, pEqual + 1, NULL); if (_tcsicmp(sLeftValue, _T("BLOCK")) == 0) m_sBlockName = sRightValue; else if (_tcsicmp(sLeftValue, _T("FLAG")) == 0) m_nControlFlag = _ttoi(sRightValue); else if (_tcsicmp(sLeftValue, _T("X")) == 0) m_xValue = _tstof(sRightValue); else if (_tcsicmp(sLeftValue, _T("Y")) == 0) m_yValue = _tstof(sRightValue); else if (_tcsicmp(sLeftValue, _T("Z")) == 0) m_zValue = _tstof(sRightValue); pBegStat = pEndStat + 1; } m_lstAttribs.Reset(); const TCHAR *pBegAttr = _tcschr(pEndBlock, _T('{')); if (!pBegAttr) return TRUE; const TCHAR *pEndAttr = _tcschr(pBegAttr, _T('}')); if (!pEndAttr) return FALSE; XString sAttrInfo(2048); GlobalFunc::_StrCpy(sAttrInfo, pBegAttr + 1, pEndAttr); pBegStat = sAttrInfo; while (pBegStat && *pBegStat) { XString sStatement(2048); TCHAR *pEndStat = _tcschr(pBegStat, _T(';')); if (!pEndStat) break; GlobalFunc::_StrCpy(sStatement, pBegStat, pEndStat); TCHAR *pEqual = _tcschr(sStatement, _T('=')); if (!pEqual) return FALSE; XString sLeftValue(2048), sRightValue(2048); GlobalFunc::_StrCpy(sLeftValue, sStatement, pEqual); GlobalFunc::_StrCpy(sRightValue, pEqual + 1, NULL); m_lstAttribs.Append(new AttribValue(sLeftValue, sRightValue)); pBegStat = pEndStat + 1; } return TRUE; } /* static BOOL IsBlockInsert(const TCHAR *pszText, AcDbObjectId &idBlock, XPoint &sizeBlock) { if(!pszText) return FALSE; int nCharNum=strlen(pszText); if(nCharNum>2 && nCharNum<256) { if(pszText[0]==_T('^') && pszText[1]==_T('B')) { TCHAR szBlockInfo[256]=_T(""); _tcscpy(szBlockInfo, &pszText[2]); TCHAR *pSep=_tcschr(szBlockInfo, _T(':')); TCHAR szBlockName[256]=_T(""), szSizeX[256]=_T(""), szSizeY[256]=_T(""); if(pSep) { StrCpy(szBlockName, szBlockInfo, pSep); pSep++; TCHAR *pSep1=_tcschr(pSep, _T(':')); if(pSep1) { StrCpy(szSizeX, pSep, pSep1); StrCpy(szSizeY, pSep1+1, NULL); } } double nSizeX=_tstof(szSizeX), nSizeY=_tstof(szSizeY); if(nSizeX 15.0001) //bAcGi = (_tcscmp(dc.Desc(), XAcGiViewDraw::Descriptor()) == 0); bAcGi = (dc.GetCommonDraw() != NULL); if (bAcGi) { OPENOBJ_BEGIN(idBlock, AcDb::kForRead, AcDbBlockTableRecord, pBlock); if (pBlock) { AcGiSubEntityTraits &traits = dc.GetCommonDraw()->subEntityTraits(); AcDbObjectId idLayer = traits.layerId(); Adesk::UInt16 nColorOld = traits.color(); AcDbObjectId idLineType = traits.lineTypeId(); AcGeMatrix3d matTrans = GlobalFunc::BlockTransform(&blkInsert); if (nColor > 0 && nColor < 256) traits.setColor(nColor); AcGiGeometry *geom = dc.GetCommonDraw()->rawGeometry(); geom->pushModelTransform(matTrans); geom->draw(pBlock); geom->popModelTransform(); traits.setLayer(idLayer); traits.setColor(nColorOld); traits.setLineType(idLineType); } OPENOBJ_END(); } else { int nOldColor = dc.GetColor(); dc.SetColor(nColor); dc.DrawEntity(blkInsert); dc.SetColor(nOldColor); } // 输出属性 AcGeMatrix3d matBlock = GlobalFunc::BlockTransform(&blkInsert); OPENOBJ_BEGIN(idBlock, AcDb::kForRead, AcDbBlockTableRecord, pBlock); if (pBlock) { AcDbBlockTableRecordIterator *pIter = NULL; if (pBlock->newIterator(pIter) == Acad::eOk && pIter) { for (pIter->start(); !pIter->done(); pIter->step()) { AcDbObjectId idAtt; pIter->getEntityId(idAtt); OPENOBJ_BEGIN(idAtt, AcDb::kForRead, AcDbAttributeDefinition, pAttr); if (pAttr) { TCHAR *pTag = pAttr->tag(); if (pTag) { AttribValue *pFind = insert.m_lstAttribs.FindNode(pTag, AttribValue::FindByName); if (pFind) { AecXDbText text; text.setPropertiesFrom(this); text.ConvertFrom(pAttr); text.SetText(pFind->m_sValue); text.setColorIndex(nColor); XPoint ptLoc = text.GetLocation(); XPoint ptHeight; ads_polar(ptLoc, nRotWcs + PI / 2, text.GetHeight(FALSE), ptHeight); ptHeight.TransformBy(matBlock); ptLoc.TransformBy(matBlock); text.SetLocation(ptLoc); text.SetHeight(ptLoc.Distance2d(ptHeight), FALSE); //text.ExplodeOrDraw2d(dc); DrawBaseEx(dc, text); } delete[] pTag; } } OPENOBJ_END(); } delete pIter; } } OPENOBJ_END(); } else { //绘制文字 double nOffset = GetCellLineSpace(nRow, nCol, FALSE); double nTextHeight = GetCellTextHeight(nRow, nCol, TRUE); AcDbObjectId idTextStyle = GetCellTextStyle(nRow, nCol); AecXDbText textLine; textLine.setPropertiesFrom(this); //Add this line on 2002/11/18 textLine.SetHeight(nTextHeight); textLine.SetStyleId(idTextStyle); textLine.SetText(pszText); AecXDbText *pCellText = NULL; const TCHAR *bHardMText = _tcschr(pszText, _T('\n')); XPoint ptMyExt = textLine.GetExtents(); BOOL bOverWidth = (ptMyExt.x + nOffset * 2.0 > w); BOOL bWrapEnabled = IsCellWrapEnabled(nRow, nCol); if (bHardMText || (bOverWidth && bWrapEnabled)) { pCellText = new AecXDbMText; pCellText->setPropertiesFrom(this); AecXDbMText &textSeg = *(AecXDbMText *)pCellText; textSeg.SetLineSpace(nOffset, FALSE); textSeg.SetPageWidth(w - 2 * nOffset, FALSE); } else { pCellText = new AecXDbText; pCellText->setPropertiesFrom(this); } Adesk::UInt16 nColor = GetCellTextColor(nRow, nCol); int nOldColor = dc.GetColor(); if (nColor > 0) { pCellText->setColorIndex(nColor); dc.SetColor(nColor); } pCellText->SetHeight(nTextHeight); pCellText->SetStyleId(idTextStyle); pCellText->SetText(pszText); InitTextInBox(*pCellText, ptBase, w, h, nOffset, GetCellHorMode(nRow, nCol), GetCellVerMode(nRow, nCol)); XPoint ptLoc = pCellText->GetLocation(); ptLoc.TransformBy(mat); pCellText->SetLocation(ptLoc); pCellText->SetRotation(m_nRotation); //if (dc.IsFullExplode()) // pCellText->ExplodeOrDraw2d(dc); //else // dc.DrawEntity(*pCellText); DrawBaseEx(dc, *pCellText); if (nColor > 0) dc.SetColor(nOldColor); delete pCellText; } } // 绘制单元格文本 void CDbSheet::DrawCellText(XPoint ptTopLeft, AcGiDraw &dc, int &nGsMarker) const { int nRowNum = GetRowNum(); int nColNum = GetColumnNum(); //INT_PTR nQuickMarker = GetQuickMarker(); for (int iRow = 0; iRow < nRowNum; iRow++) { for (int iCol = 0; iCol < nColNum; iCol++) { if (nGsMarker) { dc.SetSelectionMarker(nGsMarker); nGsMarker++; //捕捉加速 //if (nQuickMarker && (nGsMarker - 1) != nQuickMarker) // continue;//用于捕捉时加速 } DrawCellText(iRow, iCol, ptTopLeft, dc); } } int nLen = m_ranges.Length(); for (int i = 0; i < nLen; i++) { if (nGsMarker) { dc.SetSelectionMarker(nGsMarker); nGsMarker++; //捕捉加速 //if (nQuickMarker && (nGsMarker - 1) != nQuickMarker) // continue;//用于捕捉时加速 } DrawRangeText(m_ranges[i], ptTopLeft, dc); } } SubText* CDbSheet::HitTestText(XPoint pt)const { long row = HitTestOnRow(pt), col = HitTestOnColumn(pt); if (row == -1 && col >= 0 && col < GetColumnNum()) return GetSubText(0); else if (row >= 0 && row < GetRowNum() && col >= 0 && col < GetColumnNum()) { const GridCell* pCell = (*this)(row, col); if (pCell->IsRange()) { ((DList&)m_ranges).FindNode(pCell->GetRange(), CompareRange); return GetSubText(GetRowNum() * GetColumnNum() + 1 + m_ranges.CurPosition()); } else return GetSubText(row * GetColumnNum() + col + 1); } return NULL; } SubText* CDbSheet::GetSubText(long iText)const { GlobalFunc::PushMemVar vTemp(g_Option::instance().g_bExplodeSubText, TRUE); AecXDbText* pText = GetText(iText); if (pText == NULL) return NULL; SubText*pSubText = new SubText(objectId(), pText, iText); pSubText->SetMultiLine(true); if (iText != 0)//cell pSubText->SetMenuType(5); return pSubText; } void CDbSheet::SetSubText(long i, CString sText) { if (i == 0) SetTitleText(sText); else { i--; assertWriteEnabled(); if (i < GetRowNum() * GetColumnNum()) { long row = i / GetColumnNum(), col = i % GetColumnNum(); (*this)(row, col)->SetText(sText); } else { i -= GetRowNum() * GetColumnNum(); m_ranges[i]->SetText(sText); } } } long CDbSheet::GetNextSubTextIndex(long i, bool bVert, bool bPre)const { if (GetRowNum() == 0 || GetColumnNum() == 0) return i; long trueRowNum = GetRowNum() + m_title.IsVisible(); long curRow, curCol, curRowMax, curColMax; long nextRow, nextCol; if (i == 0) { curRow = curRowMax = 0; curCol = curColMax = 0; } else { i--; if (i < GetRowNum() * GetColumnNum()) { curRow = curRowMax = i / GetColumnNum() + m_title.IsVisible(); curCol = curColMax = i % GetColumnNum(); } else { i -= GetRowNum() * GetColumnNum(); const GridRange*pRange = &m_ranges[i]; curRow = pRange->GetCoord(TRUE) + m_title.IsVisible(); curCol = pRange->GetCoord(FALSE); curRowMax = pRange->GetCoordMax(TRUE) + m_title.IsVisible(); curColMax = pRange->GetCoordMax(FALSE); } } if (bVert) { if (bPre) nextRow = (curRow - 1 + trueRowNum) % trueRowNum; else nextRow = (curRowMax + 1) % trueRowNum; nextCol = curCol; } else { if (bPre) nextCol = (curCol - 1 + GetColumnNum()) % GetColumnNum(); else nextCol = (curColMax + 1) % GetColumnNum(); nextRow = curRow; } if (m_title.IsVisible()) { if (nextRow == 0) return 0; else nextRow--; } const GridCell* pCell = (*this)(nextRow, nextCol); if (pCell->IsRange()) { ((DList&)m_ranges).FindNode(pCell->GetRange(), CompareRange); return GetRowNum() * GetColumnNum() + 1 + m_ranges.CurPosition(); } else return nextRow * GetColumnNum() + nextCol + 1; } // cookies--0,标题 // 接着是正常的单元格 // 然后是合并单元格 AecXDbText * CDbSheet::GetText(Adesk::UInt32 cookies) const { AecXDbText *pDbText = NULL; if (cookies == 0) //title { if (!m_title.m_sText && !g_Option::instance().g_bExplodeSubText) return NULL; BOOL bIncludeTitle = (m_title.m_divider.m_nFlag != DividerStyle::kNone); double nTitleHeight = GetTitleHeight(FALSE); double nTitleWidth = GetSheetWidth(FALSE); //左上角为ptBase XPoint ptBase = GetTopLeft(bIncludeTitle); if (!bIncludeTitle) ads_polar(XPoint(ptBase), Layout2Wcs(m_nRotation) + PI / 2, nTitleHeight, ptBase); ads_matrix mat; ptBase.GetRotationMatrix(Layout2Wcs(m_nRotation), mat); double nOffset = GetTitleLineSpace(FALSE); double nTextHeight = GetTitleTextHeight(TRUE); AcDbObjectId idTextStyle = GetTitleTextStyle(); AecXDbText textLine; textLine.setPropertiesFrom(this); textLine.SetHeight(nTextHeight); textLine.SetStyleId(idTextStyle); textLine.SetText(m_title.m_sText); TCHAR *bHardMText = (TCHAR*)_tcschr(m_title.GetText(), _T('\n')); if (bHardMText || (textLine.GetExtents().x + nOffset * 2 > nTitleWidth && IsTitleWrapEnabled()) ) { AecXDbMText *pTextSeg = new AecXDbMText; pDbText = pTextSeg; pDbText->setPropertiesFrom(this); AecXDbMText &textSeg = *pTextSeg; textSeg.SetLineSpace(nOffset, FALSE); textSeg.SetPageWidth(nTitleWidth - 2 * nOffset, FALSE); } else { pDbText = new AecXDbText; pDbText->setPropertiesFrom(this); } Adesk::UInt16 nColor = GetTitleTextColor(); if (nColor > 0) pDbText->setColorIndex(nColor); pDbText->SetHeight(nTextHeight); pDbText->SetStyleId(idTextStyle); pDbText->SetText(m_title.m_sText); InitTextInBox(*pDbText, ptBase, nTitleWidth, nTitleHeight, nOffset, GetTitleHorMode(), GetTitleVerMode()); XPoint ptLoc = pDbText->GetLocation(); ptLoc.TransformBy(mat); pDbText->SetLocation(ptLoc); pDbText->SetRotation(m_nRotation); } else { cookies--; int nRowNum = GetRowNum(); int nColNum = GetColumnNum(); XPoint ptTopLeft = GetTopLeft(FALSE); if ((int)cookies < nRowNum * nColNum) //cells array { int nRow = cookies / nColNum; int nCol = cookies - (nRow * nColNum); const GridCell &cell = *(*this)(nRow, nCol); if (cell.IsRange()) return NULL; double x = GetColumnsWidth(0, nCol - 1, FALSE); double y = GetRowsHeight(0, nRow - 1, FALSE); double w, h; w = GetColumnWidth(nCol, FALSE); h = GetRowHeight(nRow, FALSE); //左上角为ptBase XPoint ptBase; ads_polar(ptTopLeft, Layout2Wcs(m_nRotation), x, ptBase); ads_polar(XPoint(ptBase), Layout2Wcs(m_nRotation) - PI / 2, y, ptBase); const TCHAR *pszText = cell.GetText(); if (!pszText[0] && !g_Option::instance().g_bExplodeSubText) return NULL; ads_matrix mat; ptBase.GetRotationMatrix(Layout2Wcs(m_nRotation), mat); double nOffset = GetCellLineSpace(nRow, nCol, FALSE); double nTextHeight = GetCellTextHeight(nRow, nCol, TRUE); AcDbObjectId idTextStyle = GetCellTextStyle(nRow, nCol); AecXDbText textLine; textLine.setPropertiesFrom(this); textLine.SetHeight(nTextHeight); textLine.SetStyleId(idTextStyle); textLine.SetText(pszText); TCHAR *bHardMText = (TCHAR*)_tcschr(pszText, _T('\n')); if (bHardMText || (textLine.GetExtents().x + nOffset * 2.0 > w && IsCellWrapEnabled(nRow, nCol))) { pDbText = new AecXDbMText; pDbText->setPropertiesFrom(this); AecXDbMText &textSeg = *(AecXDbMText *)pDbText; textSeg.SetLineSpace(nOffset, FALSE); textSeg.SetPageWidth(w - 2 * nOffset, FALSE); } else { pDbText = new AecXDbText; pDbText->setPropertiesFrom(this); } Adesk::UInt16 nColor = GetCellTextColor(nRow, nCol); if (nColor > 0) pDbText->setColorIndex(nColor); pDbText->SetHeight(nTextHeight); pDbText->SetStyleId(idTextStyle); pDbText->SetText(pszText); InitTextInBox(*pDbText, ptBase, w, h, nOffset, GetCellHorMode(nRow, nCol), GetCellVerMode(nRow, nCol)); XPoint ptLoc = pDbText->GetLocation(); ptLoc.TransformBy(mat); pDbText->SetLocation(ptLoc); pDbText->SetRotation(m_nRotation); } else //ranges { cookies -= nRowNum * nColNum; if ((int)cookies >= m_ranges.Length()) return NULL; const GridRange &range = m_ranges[cookies]; const TCHAR *pszText = range.GetText(); if (!pszText[0] && !g_Option::instance().g_bExplodeSubText) return NULL; double x = GetColumnsWidth(0, range.m_nColumn - 1, FALSE); double y = GetRowsHeight(0, range.m_nRow - 1, FALSE); double w, h; w = GetColumnsWidth(range.m_nColumn, range.m_nColumnMax, FALSE); h = GetRowsHeight(range.m_nRow, range.m_nRowMax, FALSE); //左上角为ptBase XPoint ptBase; ads_polar(ptTopLeft, Layout2Wcs(m_nRotation), x, ptBase); ads_polar(XPoint(ptBase), Layout2Wcs(m_nRotation) - PI / 2, y, ptBase); ads_matrix mat; ptBase.GetRotationMatrix(Layout2Wcs(m_nRotation), mat); int nRow = range.m_nRow; int nCol = range.m_nColumn; // 与正常单元格一样的处理方法 double nOffset = GetCellLineSpace(nRow, nCol, FALSE); double nTextHeight = GetCellTextHeight(nRow, nCol, TRUE); AcDbObjectId idTextStyle = GetCellTextStyle(nRow, nCol); AecXDbText textLine; textLine.setPropertiesFrom(this); textLine.SetHeight(nTextHeight); textLine.SetStyleId(idTextStyle); textLine.SetText(pszText); TCHAR *bHardMText = (TCHAR*)_tcschr(pszText, _T('\n')); if (bHardMText || (textLine.GetExtents().x + nOffset * 2.0 > w && IsCellWrapEnabled(nRow, nCol))) { pDbText = new AecXDbMText; pDbText->setPropertiesFrom(this); AecXDbMText &textSeg = *(AecXDbMText *)pDbText; textSeg.SetLineSpace(nOffset, FALSE); textSeg.SetPageWidth(w - 2 * nOffset, FALSE); } else { pDbText = new AecXDbText; pDbText->setPropertiesFrom(this); } Adesk::UInt16 nColor = GetCellTextColor(nRow, nCol); if (nColor > 0) pDbText->setColorIndex(nColor); pDbText->SetHeight(nTextHeight); pDbText->SetStyleId(idTextStyle); pDbText->SetText(pszText); InitTextInBox(*pDbText, ptBase, w, h, nOffset, GetCellHorMode(nRow, nCol), GetCellVerMode(nRow, nCol)); XPoint ptLoc = pDbText->GetLocation(); ptLoc.TransformBy(mat); pDbText->SetLocation(ptLoc); pDbText->SetRotation(m_nRotation); } } return pDbText; } // 对某一行初始化分割线的属性, 如果没有分割线则返回FALSE BOOL CDbSheet::InitRowDivider(AcDbPolyline &pline, int nRow) const { const SheetRow &row = m_rows[nRow]; if (row.m_divider.m_nFlag == DividerStyle::kNone) return FALSE; const DividerStyle ÷r = row.m_divider.m_nFlag == DividerStyle::kLocal ? row.m_divider : m_rowDivider; BOOL bRet = TRUE; pline.setPropertiesFrom(this); switch (divider.m_nFlag) { case DividerStyle::kLocal: if (!!divider.m_idLineType) pline.setLinetype(divider.m_idLineType); if (divider.m_nLineWidth > 0.0 && !!objectId()) pline.setConstantWidth(divider.m_nLineWidth * GetPScale()); if (divider.m_nColor > 0) pline.setColorIndex(divider.m_nColor); break; case DividerStyle::kParent: break; case DividerStyle::kNone: default: bRet = FALSE; break; } return bRet; } // 对某一列初始化分割线的属性, 如果没有分割线则返回FALSE BOOL CDbSheet::InitColumnDivider(AcDbPolyline &pline, int nCol) const { const SheetColumn &column = m_columns[nCol]; if (column.m_divider.m_nFlag == DividerStyle::kNone) return FALSE; const DividerStyle ÷r = column.m_divider.m_nFlag == DividerStyle::kLocal ? column.m_divider : m_colDivider; BOOL bRet = TRUE; pline.setPropertiesFrom(this); switch (divider.m_nFlag) { case DividerStyle::kLocal: if (!!divider.m_idLineType) pline.setLinetype(divider.m_idLineType); if (divider.m_nLineWidth > 0.0 && !!objectId()) pline.setConstantWidth(divider.m_nLineWidth * GetPScale()); if (divider.m_nColor > 0) pline.setColorIndex(divider.m_nColor); break; case DividerStyle::kParent: break; case DividerStyle::kNone: default: bRet = FALSE; break; } return bRet; } /////////////////////////////////////////////// // Helper Method // 强制下级继承上级属性 void CDbSheet::DescInheriGridStyle() { assertWriteEnabled(); int nRowNum = GetRowNum(); int nColNum = GetColumnNum(); for (int iRow = 0; iRow < nRowNum; iRow++) { SheetRow *pRow = m_rows[iRow]; pRow->m_nVerMode = AcDb::kTextBase; } for (int iCol = 0; iCol < nColNum; iCol++) { SheetColumn *pCol = m_columns[iCol]; pCol->m_gridStyle.SetOverrideAll(FALSE); } for (iRow = 0; iRow < nRowNum; iRow++) { for (iCol = 0; iCol < nColNum; iCol++) { GridCell *pCell = (*this)(iRow, iCol); GridStyle &grid = pCell->GetGridStyle(); grid.SetOverrideAll(FALSE); } } } // 下属行继承特性 void CDbSheet::DescInheritRowDivider(bool bIncludeRowHeight) { assertWriteEnabled(); int nRowNum = GetRowNum(); for (int iRow = 0; iRow < nRowNum; iRow++) { SheetRow *pRow = m_rows[iRow]; pRow->m_divider.SetDividerFlag(DividerStyle::kParent); if (bIncludeRowHeight) { pRow->SetHeight(m_nRowHeight); pRow->SetRowHeightStyle(SheetRow::kParent); } } } void CDbSheet::DescInheritColDivider() { assertWriteEnabled(); int nColNum = GetColumnNum(); for (int iCol = 0; iCol < nColNum; iCol++) { m_columns[iCol]->m_divider.SetDividerFlag(DividerStyle::kParent); } } void CDbSheet::DescInheritColGridStyle(int iCol) { assertWriteEnabled(); int nRowNum = GetRowNum(); for (int iRow = 0; iRow < nRowNum; iRow++) { GridCell *pCell = (*this)(iRow, iCol); GridStyle &grid = pCell->GetGridStyle(); BOOL bOver = grid.TestFlagBit(OF_VERMODE); grid.SetOverrideAll(FALSE); if (bOver) { grid.SetFlagBit(OF_VERMODE, TRUE); } } } void CDbSheet::DescInheritRowGridStyle(int iRow) { assertWriteEnabled(); int nColNum = GetColumnNum(); for (int iCol = 0; iCol < nColNum; iCol++) { GridCell *pCell = (*this)(iRow, iCol); GridStyle &grid = pCell->GetGridStyle(); grid.SetFlagBit(OF_VERMODE, FALSE); } } XPoint CDbSheet::Align2Base(XPoint ptAlign, XPoint ext) const { XPoint ptBase = AcGiDraw::Align2Base(m_nAlignment, ptAlign, ext); ads_matrix mat; ptAlign.GetRotationMatrix(Layout2Wcs(m_nRotation), mat); ptBase.TransformBy(mat); return ptBase; } XPoint CDbSheet::Base2Align(XPoint ptBase, XPoint ext) const { XPoint ptAlign = AcGiDraw::Base2Align(m_nAlignment, ptBase, ext); ads_matrix mat; ptBase.GetRotationMatrix(Layout2Wcs(m_nRotation), mat); ptAlign.TransformBy(mat); return ptAlign; } // 按行列取得单元格 GridCell * CDbSheet::operator () (int nRow, int nCol) { return &m_pCells[nRow * GetColumnNum() + nCol]; } // 按行列取得单元格 const GridCell * CDbSheet::operator () (int nRow, int nCol) const { CDbSheet *pThis = (CDbSheet *)this; return (*pThis)(nRow, nCol); } int CDbSheet::HitTestOnColumn(XPoint pt) const { pt.z = 0; int nColNum = m_columns.Length(); XPoint ptTopLeft = GetTopLeft(FALSE); double nColWidth = 0.0; double nRotWcs = Layout2Wcs(m_nRotation); for (int n = 0; n < nColNum; n++) { XLine lnLeft(ptTopLeft, nRotWcs + PI / 2); nColWidth = GetColumnWidth(n, FALSE); ads_polar(XPoint(ptTopLeft), nRotWcs, nColWidth, ptTopLeft); XLine lnRight(ptTopLeft, nRotWcs + PI / 2); int nSide1 = lnLeft.OnWhichSide(pt); int nSide2 = lnRight.OnWhichSide(pt); if (nSide1 == OFFSET_LEFT && n == 0) return COL_PREVFIRST; if (nSide1 == OFFSET_RIGHT && nSide2 == OFFSET_LEFT) { double d1 = pt.Distance(&lnLeft), d2 = pt.Distance(&lnRight); double distPre = (d1 + d2) / 20.0; if (d1 < distPre || d2 < distPre) return COL_NEXTLAST; return n; } } return COL_NEXTLAST; } int CDbSheet::HitTestOnRow(XPoint pt) const { pt.z = 0; int nRowNum = m_rows.Length(); XPoint ptTopLeft = GetTopLeft(FALSE); double nRotWcs = Layout2Wcs(m_nRotation); for (int n = 0; n < nRowNum; n++) { XLine lnUp(ptTopLeft, nRotWcs); double nRowHeight = GetRowHeight(n, FALSE); ads_polar(XPoint(ptTopLeft), nRotWcs - PI / 2, nRowHeight, ptTopLeft); XLine lnDown(ptTopLeft, nRotWcs); int nSide1 = lnUp.OnWhichSide(pt); int nSide2 = lnDown.OnWhichSide(pt); if (nSide1 == OFFSET_LEFT && n == 0) { double d = GetTitleHeight(FALSE); double d1 = pt.Distance(&lnUp); double d2 = d - d1; double distPre = (d1 + d2) / 20.0; if (d1 < distPre || d2 < distPre) return COL_NEXTLAST; return ROW_PREVFIRST; } if (nSide1 == OFFSET_RIGHT && nSide2 == OFFSET_LEFT) { double d1 = pt.Distance(&lnUp), d2 = pt.Distance(&lnDown); double distPre = (d1 + d2) / 20.0; if (d1 < distPre || d2 < distPre) return COL_NEXTLAST; return n; } } return ROW_NEXTLAST; } const GridCell * CDbSheet::HitTestOnCell(XPoint pt, int *pRow, int *pCol) const { pt.z = 0; int nRowNum = GetRowNum(); int nColNum = GetColumnNum(); double nRotWcs = Layout2Wcs(m_nRotation); for (int iRow = 0; iRow < nRowNum; iRow++) { for (int iCol = 0; iCol < nColNum; iCol++) { XPoint ptTopLeft = GetCellPoint(iRow, iCol); XPoint szCell = GetCellSize(iRow, iCol, FALSE); XPoint ptBotLeft, ptBotRight, ptTopRight; ads_polar(ptTopLeft, nRotWcs, szCell.x, ptTopRight); ads_polar(ptTopLeft, nRotWcs - PI / 2, szCell.y, ptBotLeft); ads_polar(ptTopRight, nRotWcs - PI / 2, szCell.y, ptBotRight); XPoly2D poly(1); poly.AppendNode(ptTopLeft); poly.AppendNode(ptBotLeft); poly.AppendNode(ptBotRight); poly.AppendNode(ptTopRight); poly.SetElevation(0.0); if ((pt & poly) == PR_INSIDE) { if (pRow) *pRow = iRow; if (pCol) *pCol = iCol; return (*this)(iRow, iCol); } } } return NULL; } // 单元分解 BOOL CDbSheet::ExplodeCell(int nRow, int nCol) { assertWriteEnabled(); GridCell *pCell = (*this)(nRow, nCol); if (!pCell || !pCell->GetRange()) return FALSE; const GridRange *pRange = pCell->GetRange(); for (int iRow = pRange->GetCoord(TRUE); iRow <= pRange->GetCoordMax(TRUE); iRow++) { for (int iCol = pRange->GetCoord(FALSE); iCol <= pRange->GetCoordMax(FALSE); iCol++) { GridCell *pCell0 = (*this)(iRow, iCol); if (pCell0) { GlobalFunc::CopyObject(*(GridCell *)pRange, *pCell0); pCell0->SetRange(NULL); } } } int nRanNum = m_ranges.Length(); for (int i = 0; i < nRanNum; i++) { if (m_ranges[i] == pRange) { m_ranges.Remove(); break; } } return TRUE; } // 合并单元格 void CDbSheet::MergeCells(int nRowFrom, int nColFrom, int nRowTo, int nColTo) { assertWriteEnabled(); if (nRowTo < nRowFrom || nColTo < nColFrom) return; if (nRowFrom == nRowTo && nColFrom == nColTo) return; GridRange *pRange = NULL; GridCell *pMaster = (*this)(nRowFrom, nColFrom); //左上角 if (pMaster->IsRange()) { pRange = (GridRange *)pMaster->GetRange(); ASSERT(pRange->GetCoord(TRUE) == nRowFrom && pRange->GetCoord(FALSE) == nColFrom); ASSERT(pRange->GetCoordMax(TRUE) <= nRowTo); ASSERT(pRange->GetCoordMax(FALSE) <= nColTo); pRange->SetCoord(nRowFrom, nColFrom); pRange->SetCoordMax(nRowTo, nColTo); } else { pRange = new GridRange; GlobalFunc::CopyObject(pMaster->m_gridStyle, pRange->m_gridStyle); pRange->m_gridStyle.SetFlagBit(OF_HORMODE); pRange->m_gridStyle.SetFlagBit(OF_VERMODE); pRange->m_gridStyle.SetHorMode(AcDb::kTextCenter); pRange->m_gridStyle.SetVerMode(AcDb::kTextVertMid); pRange->SetText(pMaster->GetText()); pRange->SetCoord(nRowFrom, nColFrom); pRange->SetCoordMax(nRowTo, nColTo); m_ranges.Append(pRange); } for (int iRow = nRowFrom; iRow <= nRowTo; iRow++) { for (int iCol = nColFrom; iCol <= nColTo; iCol++) { GridCell *pSlaver = (*this)(iRow, iCol); if (pSlaver->IsRange()) { //其他的合并单元格,则予以删除 const GridRange *pSlaverRange = pSlaver->GetRange(); if (pSlaverRange != pRange) { if (m_ranges.FindNode(pSlaverRange, CompareRange)) m_ranges.Remove(); } } pSlaver->SetRange(pRange); } } } void CDbSheet::CalculateRowHeight(int nRowFrom, int nRowTo) { assertWriteEnabled(); for (int i = nRowFrom; i <= nRowTo; i++) CalculateRowHeight(i); } //当行的文字改变时, 重新计算行高 void CDbSheet::CalculateRowHeight(int nRow) { assertWriteEnabled(); SheetRow *row = m_rows[nRow]; if (row->GetRowHeightStyle() == SheetRow::kAutomatic) { int nColNum = GetColumnNum(); XPoint ptTopLeft = GetTopLeft(FALSE); double nSizeHeight = 0.0; //row->GetHeight()*GetPScale(); for (int iCol = 0; iCol < nColNum; iCol++) { double nOffset = GetCellLineSpace(nRow, iCol, FALSE); const TCHAR *szText = (*this)(nRow, iCol)->GetText(); /* AcDbObjectId idBlock; XPoint sizeBlock; if(IsBlockInsert(szText, idBlock, sizeBlock)) { if(nSizeHeight<1.0E-3) nSizeHeight= sizeBlock.y+nOffset*2.0; else nSizeHeight = max(nSizeHeight, sizeBlock.y+nOffset*2.0); continue; }*/ const AcDbVoidPtrArray *entSet; AcGiViewDraw dc; DrawCellText(nRow, iCol, ptTopLeft, dc); entSet = _Get2DBuffer(); int nCount = entSet->length(); if (nCount > 0) { AcDbEntity *pEnt = (AcDbEntity *)entSet->at(0); if (pEnt->isKindOf(AecXDbText::desc())) { AecXDbText *pText = (AecXDbText *)pEnt; XPoint ext = pText->GetExtents(); if (nSizeHeight < 1.0E-3) nSizeHeight = ext.y + nOffset * 2.0; else nSizeHeight = max(nSizeHeight, ext.y + nOffset * 2.0); } /*else if(pEnt->isKindOf(AcDbBlockReference::desc())) { BlockGeomInfo info; info.SetFromInsert(AcDbBlockReference::cast(pEnt)); double nOffset=GetCellLineSpace(nRow, iCol, FALSE); if(nSizeHeight<1.0E-3) nSizeHeight= info.GetSizeY()+nOffset*2.0; else nSizeHeight = max(nSizeHeight, info.GetSizeY()+nOffset*2.0); }*/ } } if (nSizeHeight > 1.0E-3) row->SetHeight(nSizeHeight / GetPScale()); } } // 复制行内容和属性(包括单元格) BOOL CDbSheet::CopyRow(int nSrc, int nDest) { //add by whl on 060223 if (nSrc < 0 || nSrc >= GetRowNum() || nDest < 0 || nDest >= GetRowNum()) return FALSE; assertWriteEnabled(); SheetRow *rowSrc = m_rows[nSrc]; SheetRow *rowDest = m_rows[nDest]; GlobalFunc::CopyObject(*rowSrc, *rowDest); int nColNum = GetColumnNum(); //add by xlc on 071224 SHArray nPosArray; //记录合并单元格的位置数组 for (int i = 0; i < nColNum; i++) { GridCell *cellSrc = (*this)(nSrc, i); GridCell *cellDest = (*this)(nDest, i); const GridRange *pRange = cellDest->GetRange(); const GridRange *pRangeSrc = cellSrc->GetRange(); const GridCell *pSrc = pRangeSrc ? (const GridCell *)pRangeSrc : (const GridCell *)cellSrc; if (pRange) GlobalFunc::CopyObject(*pSrc, *(GridCell *)pRange); else GlobalFunc::CopyObject(*pSrc, *cellDest); //add by xlc on 071224 if (pRangeSrc) { GridRange *pRange1 = (GridRange *)pRangeSrc; int colIndexMin = pRange1->GetCoord(FALSE); int colIndexMax = pRange1->GetCoordMax(FALSE); int nNum = nPosArray.GetLength(); if (nNum < 1 || colIndexMin > nPosArray[nNum - 1]) { nPosArray.AddTail(colIndexMin); nPosArray.AddTail(colIndexMax); } } } //add by xlc on 071224 //合并单元格 for (i = 0; i < nPosArray.GetLength() - 1;) { MergeCells(nDest, nPosArray[i], nDest, nPosArray[i + 1]); i = i + 2; } return TRUE; } // 交换列 BOOL CDbSheet::SwapColumn(int nSrc, int nDest) { assertWriteEnabled(); SheetColumn *colSrc = m_columns[nSrc]; SheetColumn *colDest = m_columns[nDest]; GlobalFunc::Exchange(*colSrc, *colDest); int nRowNum = GetRowNum(); for (int i = nRowNum - 1; i >= 0; i--) { GridCell *cellSrc = (*this)(i, nSrc); GridCell *cellDest = (*this)(i, nDest); const GridRange *pRangeSrc = cellSrc->GetRange(); const GridRange *pRangeDest = cellDest->GetRange(); GridCell cellTemp; if (pRangeSrc) { GlobalFunc::CopyObject(*(const GridCell *)pRangeSrc, cellTemp); if (pRangeDest) { if (i == pRangeSrc->GetCoord(TRUE)) GlobalFunc::CopyObject(*(const GridCell*)pRangeDest, *(GridCell *)pRangeSrc); if (i == pRangeDest->GetCoord(TRUE)) GlobalFunc::CopyObject(cellTemp, *(GridCell *)pRangeDest); } else { if (i == pRangeSrc->GetCoord(TRUE)) GlobalFunc::CopyObject(*cellDest, *(GridCell *)pRangeSrc); GlobalFunc::CopyObject(cellTemp, *cellDest); } } else { GlobalFunc::CopyObject(*cellSrc, cellTemp); if (pRangeDest) { GlobalFunc::CopyObject(*(const GridCell*)pRangeDest, *cellSrc); if (i == pRangeDest->GetCoord(TRUE)) GlobalFunc::CopyObject(cellTemp, *(GridCell *)pRangeDest); } else { GlobalFunc::CopyObject(*cellDest, *cellSrc); GlobalFunc::CopyObject(cellTemp, *cellDest); } } cellSrc->SetRange((GridRange *)pRangeSrc); cellDest->SetRange((GridRange *)pRangeDest); } return TRUE; } // 交换行 BOOL CDbSheet::SwapRow(int nSrc, int nDest) { assertWriteEnabled(); SheetRow *rowSrc = m_rows[nSrc]; SheetRow *rowDest = m_rows[nDest]; GlobalFunc::Exchange(*rowSrc, *rowDest); int nColNum = GetColumnNum(); for (int i = nColNum - 1; i >= 0; i--) { GridCell *cellSrc = (*this)(nSrc, i); GridCell *cellDest = (*this)(nDest, i); const GridRange *pRangeSrc = cellSrc->GetRange(); const GridRange *pRangeDest = cellDest->GetRange(); GridCell cellTemp; if (pRangeSrc) { GlobalFunc::CopyObject(*(const GridCell *)pRangeSrc, cellTemp); if (pRangeDest) { if (i == pRangeSrc->GetCoord(FALSE)) GlobalFunc::CopyObject(*(const GridCell*)pRangeDest, *(GridCell *)pRangeSrc); if (i == pRangeDest->GetCoord(FALSE)) GlobalFunc::CopyObject(cellTemp, *(GridCell *)pRangeDest); } else { if (i == pRangeSrc->GetCoord(FALSE)) GlobalFunc::CopyObject(*cellDest, *(GridCell *)pRangeSrc); GlobalFunc::CopyObject(cellTemp, *cellDest); } } else { GlobalFunc::CopyObject(*cellSrc, cellTemp); if (pRangeDest) { GlobalFunc::CopyObject(*(const GridCell*)pRangeDest, *cellSrc); if (i == pRangeDest->GetCoord(FALSE)) GlobalFunc::CopyObject(cellTemp, *(GridCell *)pRangeDest); } else { GlobalFunc::CopyObject(*cellDest, *cellSrc); GlobalFunc::CopyObject(cellTemp, *cellDest); } } cellSrc->SetRange((GridRange *)pRangeSrc); cellDest->SetRange((GridRange *)pRangeDest); } return TRUE; } // 排序 //-1代表最后一列 void CDbSheet::SortByColumn(int nKeyCol, BOOL bSortAscend, int nRowFrom, int nRowTo) { if (nRowTo < 0) nRowTo = GetRowNum() - 1; for (int i = nRowFrom; i <= nRowTo; i++) { for (int j = nRowFrom; j < nRowTo; j++) { GridCell *pCell1 = (*this)(i, nKeyCol); GridCell *pCell2 = (*this)(j, nKeyCol); int nCmp = _tcscmp(pCell1->GetText(), pCell2->GetText()); if ((bSortAscend && nCmp > 0) || (!bSortAscend && nCmp < 0)) SwapRow(i, j); } } } //-1代表最后一列 void CDbSheet::SortByColumns(const DList &lstKeyCol, BOOL bSortAscend, int nRowFrom, int nRowTo) { if (nRowTo < 0) nRowTo = GetRowNum() - 1; int nColNum = lstKeyCol.Length(); for (int i = nRowFrom; i <= nRowTo; i++) { for (int j = nRowFrom; j < nRowTo; j++) { int nCmp = 0; for (int n = 0; n < nColNum; n++) { int nKeyCol = lstKeyCol[n]; GridCell *pCell1 = (*this)(i, nKeyCol); GridCell *pCell2 = (*this)(j, nKeyCol); int nCmp1 = _tcscmp(pCell1->GetText(), pCell2->GetText()); if (nCmp1 != 0) { nCmp = nCmp1; break; } } if ((bSortAscend && nCmp > 0) || (!bSortAscend && nCmp < 0)) SwapRow(i, j); } } } // 删除列 void CDbSheet::RemoveColumn(int nCol) { assertWriteEnabled(); ASSERT(m_pCells); int nRowNum = GetRowNum(); int nColNum = GetColumnNum(); if (nColNum <= 1) return; GridCell *pCellArray = new GridCell[nRowNum * (nColNum - 1)]; for (int iCol = 0; iCol < nCol; iCol++) { for (int iRow = 0; iRow < nRowNum; iRow++) { pCellArray[iRow * (nColNum - 1) + iCol] = m_pCells[iRow * nColNum + iCol]; } } for (iCol = nCol + 1; iCol < nColNum; iCol++) { for (int iRow = 0; iRow < nRowNum; iRow++) { pCellArray[iRow * (nColNum - 1) + iCol - 1] = m_pCells[iRow * nColNum + iCol]; } } delete[]m_pCells; m_pCells = pCellArray; m_columns.Remove(nCol); int nRanNum = m_ranges.Length(); for (int iRan = 0; iRan < nRanNum; iRan++) { GridRange *pRange = m_ranges[iRan]; if (pRange->GetCoord(FALSE) == pRange->GetCoordMax(FALSE) && pRange->GetCoord(FALSE) == nCol) { //整个单元格在列内 m_ranges.Remove(); nRanNum--; iRan--; } else if (pRange->GetCoord(FALSE) > nCol) { //单元格在右边 ASSERT(pRange->GetCoordMax(FALSE) > nCol); pRange->SetCoord(pRange->GetCoord(TRUE), pRange->GetCoord(FALSE) - 1); pRange->SetCoordMax(pRange->GetCoordMax(TRUE), pRange->GetCoordMax(FALSE) - 1); } else if (pRange->GetCoord(FALSE) <= nCol && pRange->GetCoordMax(FALSE) >= nCol) { // 跨越列 pRange->SetCoordMax(pRange->GetCoordMax(TRUE), pRange->GetCoordMax(FALSE) - 1); if (pRange->IsCellar()) { // 合并单元格退化为单元格 (*this)(pRange->GetCoord(TRUE), pRange->GetCoord(FALSE))->SetRange(NULL); //add by whl on 040902,解决bug:删除列时原先的合并单元退化时丢文字 (*this)(pRange->GetCoord(TRUE), pRange->GetCoord(FALSE))->SetText(pRange->GetText()); m_ranges.Remove(); nRanNum--; iRan--; } } else { ASSERT(pRange->GetCoordMax(FALSE) < nCol); //单元格在左边 ASSERT(pRange->GetCoord(FALSE) < nCol); // 不发生任何改动 } } // 重新计算行高度 CalculateRowHeight(0, GetRowNum() - 1); } // 删除行 void CDbSheet::RemoveRow(int nRow) { assertWriteEnabled(); ASSERT(m_pCells); int nRowNum = GetRowNum(); int nColNum = GetColumnNum(); if (nColNum < 1 || nRow < 0 || nRow >= nRowNum) return; GridCell *pCellArray = new GridCell[(nRowNum - 1) * nColNum]; for (int iRow = 0; iRow < nRow; iRow++) { for (int iCol = 0; iCol < nColNum; iCol++) { pCellArray[iRow * nColNum + iCol] = m_pCells[iRow * nColNum + iCol]; } } for (iRow = nRow + 1; iRow < nRowNum; iRow++) { for (int iCol = 0; iCol < nColNum; iCol++) { pCellArray[(iRow - 1) * nColNum + iCol] = m_pCells[iRow * nColNum + iCol]; } } delete[]m_pCells; m_pCells = pCellArray; m_rows.Remove(nRow); int nRanNum = m_ranges.Length(); for (int iRan = 0; iRan < nRanNum; iRan++) { GridRange *pRange = m_ranges[iRan]; if (pRange->GetCoord(TRUE) == pRange->GetCoordMax(TRUE) && pRange->GetCoord(TRUE) == nRow) { //单元范围在此行内 m_ranges.Remove(); nRanNum--; iRan--; } else if (pRange->GetCoord(TRUE) > nRow) { //单元格在下边 ASSERT(pRange->GetCoordMax(TRUE) > nRow); pRange->SetCoord(pRange->GetCoord(TRUE) - 1, pRange->GetCoord(FALSE)); pRange->SetCoordMax(pRange->GetCoordMax(TRUE) - 1, pRange->GetCoordMax(FALSE)); } else if (pRange->GetCoord(TRUE) <= nRow && pRange->GetCoordMax(TRUE) >= nRow) { // 跨越列 pRange->SetCoordMax(pRange->GetCoordMax(TRUE) - 1, pRange->GetCoordMax(FALSE)); if (pRange->IsCellar()) { // 合并单元格退化为单元格 (*this)(pRange->GetCoord(TRUE), pRange->GetCoord(FALSE))->SetRange(NULL); //add by whl on 040902,解决bug:删除行时原先的合并单元退化时丢文字 (*this)(pRange->GetCoord(TRUE), pRange->GetCoord(FALSE))->SetText(pRange->GetText()); m_ranges.Remove(); nRanNum--; iRan--; } } else { ASSERT(pRange->GetCoordMax(TRUE) < nRow); //单元格在左边 ASSERT(pRange->GetCoord(TRUE) < nRow); // 不发生任何改动 } } } BOOL CDbSheet::AddRowAt(int i) { SheetRow row; if (i >= 0 && i < GetRowNum()) { GlobalFunc::CopyObject(*GetRow(i), row); } else { row.SetHeight(m_nRowHeight); row.SetRowHeightStyle(SheetRow::kParent); row.SetVerMode(m_gridStyle.GetVerMode()); row.SeDividerStyle(m_rowDivider); } return AddRowAt(i, row); } // 增加第i行 BOOL CDbSheet::AddRowAt(int i, const SheetRow &row) { assertWriteEnabled(); ASSERT(i >= 0); int nRowNum = GetRowNum(); int nColNum = GetColumnNum(); if (nColNum < 1) return FALSE; SheetRow *pRow = new SheetRow; VERIFY(GlobalFunc::CopyObject(row, *pRow)); if (i < m_rows.Length()) { m_rows[i]; m_rows.Insert(pRow); } else { m_rows.Append(pRow); } GridCell *pCellArray = new GridCell[(nRowNum + 1) * nColNum]; for (int iRow = 0; iRow < i; iRow++) { for (int iCol = 0; iCol < nColNum; iCol++) { pCellArray[iRow * nColNum + iCol] = m_pCells[iRow * nColNum + iCol]; } } for (iRow = i; iRow < nRowNum; iRow++) { for (int iCol = 0; iCol < nColNum; iCol++) { pCellArray[(iRow + 1) * nColNum + iCol] = m_pCells[iRow * nColNum + iCol]; } } if (m_pCells) delete[]m_pCells; m_pCells = pCellArray; int nRanNum = m_ranges.Length(); for (int iRan = 0; iRan < nRanNum; iRan++) { GridRange *pRange = m_ranges[iRan]; if (pRange->GetCoord(TRUE) >= i) { //在新增行后面 //if(pRange->GetCoord(TRUE)>i) pRange->SetCoord(pRange->GetCoord(TRUE) + 1, pRange->GetCoord(FALSE)); pRange->SetCoordMax(pRange->GetCoordMax(TRUE) + 1, pRange->GetCoordMax(FALSE)); } else if (pRange->GetCoordMax(TRUE) >= i) { //跨越新增的行 pRange->SetCoordMax(pRange->GetCoordMax(TRUE) + 1, pRange->GetCoordMax(FALSE)); for (int idx = pRange->GetCoord(FALSE); idx <= pRange->GetCoordMax(FALSE); idx++) { (*this)(i, idx)->SetRange(pRange); } } } return TRUE; } // 增加第i列 BOOL CDbSheet::AddColumnAt(int i) { SheetColumn col; int nColNum = GetColumnNum(); if (i >= 0 && i < nColNum) { GlobalFunc::CopyObject(*GetColumn(i), col); } else if (i == nColNum) { GlobalFunc::CopyObject(*GetColumn(nColNum - 1), col); } else { ASSERT(0); /* col.SetWidth(24.0); col.SetGridStyle(m_gridStyle); col.SeDividerStyle(m_colDivider); */ return FALSE; } return AddColumnAt(i, col); } BOOL CDbSheet::AddColumnAt(int i, const SheetColumn &column) { assertWriteEnabled(); ASSERT(i >= 0); int nRowNum = GetRowNum(); int nColNum = GetColumnNum(); if (nRowNum <= 1) return FALSE; SheetColumn *pCol = new SheetColumn; VERIFY(GlobalFunc::CopyObject(column, *pCol)); if (i < m_columns.Length()) { m_columns[i]; m_columns.Insert(pCol); } else { m_columns.Append(pCol); } // 复制已有的列 GridCell *pCellArray = new GridCell[nRowNum * (nColNum + 1)]; for (int iRow = 0; iRow < nRowNum; iRow++) { for (int iCol = 0; iCol < i; iCol++) { pCellArray[iRow * (nColNum + 1) + iCol] = m_pCells[iRow * nColNum + iCol]; } for (iCol = i; iCol < nColNum; iCol++) { pCellArray[iRow * (nColNum + 1) + iCol + 1] = m_pCells[iRow * nColNum + iCol]; } } if (m_pCells) delete[]m_pCells; m_pCells = pCellArray; // int nRanNum = m_ranges.Length(); for (int iRan = 0; iRan < nRanNum; iRan++) { GridRange *pRange = m_ranges[iRan]; if (pRange->GetCoord(FALSE) >= i) { //单元格在新增列后面 pRange->SetCoord(pRange->GetCoord(TRUE), pRange->GetCoord(FALSE) + 1); pRange->SetCoordMax(pRange->GetCoordMax(TRUE), pRange->GetCoordMax(FALSE) + 1); } else if (pRange->GetCoordMax(FALSE) >= i) { //单元格跨越新增的列 pRange->SetCoordMax(pRange->GetCoordMax(TRUE), pRange->GetCoordMax(FALSE) + 1); for (int idx = pRange->GetCoord(TRUE); idx <= pRange->GetCoordMax(TRUE); idx++) { (*this)(idx, i)->SetRange(pRange); } } } return TRUE; } //add by whl on 040903 void CDbSheet::Merge(CDbSheet*pSheet, bool bRowMerge) { assertWriteEnabled(); CDbSheet*pSheet1 = (CDbSheet*)(pSheet->clone()); DList &m_columns1 = pSheet1->m_columns; DList &m_rows1 = pSheet1->m_rows; DList &m_ranges1 = pSheet1->m_ranges; GridCell *m_pCells1 = pSheet1->m_pCells; if (bRowMerge) { long newRowNum = GetRowNum() + pSheet->GetRowNum(), newColNum = max(GetColumnNum(), pSheet->GetColumnNum()); //复制单元格 GridCell *pNewCells = new GridCell[newRowNum * newColNum]; for (long i = 0; i < GetRowNum(); i++) for (long j = 0; j < GetColumnNum(); j++) pNewCells[i * newColNum + j] = m_pCells[i * GetColumnNum() + j]; for (i = 0; i < pSheet->GetRowNum(); i++) for (long j = 0; j < pSheet->GetColumnNum(); j++) pNewCells[(i + GetRowNum()) * newColNum + j] = m_pCells1[i * pSheet->GetColumnNum() + j]; delete[] m_pCells; m_pCells = pNewCells; //加列 for (i = GetColumnNum(); i < newColNum; i++) m_columns.Append(new SheetColumn(*m_columns1[i])); //调整并入合并单元记录 for (i = 0; i < m_ranges1.Length(); i++) { GridRange *pRange = m_ranges1[i]; pRange->SetCoord(pRange->GetCoord(TRUE) + GetRowNum(), pRange->GetCoord(FALSE)); pRange->SetCoordMax(pRange->GetCoordMax(TRUE) + GetRowNum(), pRange->GetCoordMax(FALSE)); } m_ranges << m_ranges1; //加行 m_rows << m_rows1; } else { long newRowNum = max(GetRowNum(), pSheet->GetRowNum()), newColNum = GetColumnNum() + pSheet->GetColumnNum(); //复制单元格 GridCell *pNewCells = new GridCell[newRowNum * newColNum]; for (long i = 0; i < GetRowNum(); i++) for (long j = 0; j < GetColumnNum(); j++) pNewCells[i * newColNum + j] = m_pCells[i * GetColumnNum() + j]; for (i = 0; i < pSheet->GetRowNum(); i++) for (long j = 0; j < pSheet->GetColumnNum(); j++) pNewCells[i * newColNum + j + GetColumnNum()] = m_pCells1[i * pSheet->GetColumnNum() + j]; delete[] m_pCells; m_pCells = pNewCells; //加行 for (i = GetRowNum(); i < newRowNum; i++) m_rows.Append(new SheetRow(*m_rows1[i])); //调整并入合并单元记录 for (i = 0; i < m_ranges1.Length(); i++) { GridRange *pRange = m_ranges1[i]; pRange->SetCoord(pRange->GetCoord(TRUE), pRange->GetCoord(FALSE) + GetColumnNum()); //modify by xlc on 071220 //pRange->SetCoordMax(pRange->GetCoordMax(TRUE)+GetRowNum(),pRange->GetCoordMax(FALSE)+GetColumnNum()); pRange->SetCoordMax(pRange->GetCoordMax(TRUE), pRange->GetCoordMax(FALSE) + GetColumnNum()); } m_ranges << m_ranges1; //加行 m_columns << m_columns1; } CalculateRowHeight(0, GetRowNum() - 1); delete pSheet1; } ///////////////////////////////////////////////////////////////// // Properties const DividerStyle& CDbSheet::GetRowDivider() const { return m_rowDivider; } const DividerStyle& CDbSheet::GetColDivider() const { return m_colDivider; } GridStyle & CDbSheet::GetGridStyle() { return m_gridStyle; } DividerStyle & CDbSheet::GetRowDivider() { return m_rowDivider; } DividerStyle & CDbSheet::GetColDivider() { return m_colDivider; } DividerStyle & CDbSheet::GetBorderStyle() { return m_border; } const DividerStyle & CDbSheet::GetBorderStyle() const { return m_border; } int CDbSheet::GetRowNum() const { return m_rows.Length(); } int CDbSheet::GetColumnNum() const { return m_columns.Length(); } const SheetRow * CDbSheet::GetRow(int nRow) const { return &m_rows[nRow]; } const SheetColumn * CDbSheet::GetColumn(int nCol) const { return &m_columns[nCol]; } SheetRow * CDbSheet::GetRow(int nRow) { return m_rows[nRow]; } SheetColumn * CDbSheet::GetColumn(int nCol) { return m_columns[nCol]; } const GridStyle & CDbSheet::GetGridStyle() const { return m_gridStyle; } void CDbSheet::SetBorderStyle(const DividerStyle& src) { assertWriteEnabled(); GlobalFunc::CopyObject(src, m_border); } void CDbSheet::SetRowDivider(const DividerStyle& src) { assertWriteEnabled(); GlobalFunc::CopyObject(src, m_rowDivider); } void CDbSheet::SetColDivider(const DividerStyle& src) { assertWriteEnabled(); GlobalFunc::CopyObject(src, m_colDivider); } void CDbSheet::SetGridStyle(const GridStyle &src) { assertWriteEnabled(); GlobalFunc::CopyObject(src, m_gridStyle); } // 增加第i列 // 没有检查列的数目 BOOL CDbSheet::SetColumnAt(int i, const SheetColumn &column) { assertWriteEnabled(); ASSERT(i >= 0); SheetColumn *pCol = m_columns[i]; VERIFY(GlobalFunc::CopyObject(column, *pCol)); return TRUE; } // 增加地i行 BOOL CDbSheet::SetRowAt(int i, const SheetRow &row) { assertWriteEnabled(); ASSERT(i >= 0); SheetRow *pRow = m_rows[i]; VERIFY(GlobalFunc::CopyObject(row, *pRow)); return TRUE; } void CDbSheet::GetBorder(XPoly2D &polyBorder) const { double nRotWcs = Layout2Wcs(m_nRotation); BOOL bIncludeTitle = (m_title.IsVisible() && m_title.GetDividerStyle().GetDividerFlag() != DividerStyle::kNone); XPoint ptUpLeft = GetTopLeft(bIncludeTitle); XPoint ext = GetExtents(bIncludeTitle, FALSE); XPoint ptLowRight, ptUpRight, ptLowLeft; ads_polar(ptUpLeft, nRotWcs - PI / 2, ext.y, ptLowLeft); ads_polar(ptLowLeft, nRotWcs, ext.x, ptLowRight); ads_polar(ptLowRight, nRotWcs + PI / 2, ext.y, ptUpRight); polyBorder.Reset(); polyBorder.AppendNode(ptLowLeft); polyBorder.AppendNode(ptLowRight); polyBorder.AppendNode(ptUpRight); polyBorder.AppendNode(ptUpLeft); polyBorder.SetFlag(1); //polyBorder.SetElevation(0.0); } // 取得表格大小 XPoint CDbSheet::GetExtents(BOOL bIncludeTitle, BOOL bAsPaperUnit) const { double nWidth = GetSheetWidth(bAsPaperUnit); double nHeight = GetSheetHeight(bIncludeTitle, bAsPaperUnit); return XPoint(nWidth, nHeight); } // 取得表格的高度 double CDbSheet::GetSheetHeight(BOOL bIncludeTitle, BOOL bAsPaperUnit) const { int nRowNum = m_rows.Length(); double nHeight = GetRowsHeight(0, nRowNum - 1, TRUE); if (bIncludeTitle) nHeight += m_title.GetHeight(); if (!bAsPaperUnit) { double nScale = GetPScale(); nHeight *= nScale; } return nHeight; } // 取得表格的宽度 double CDbSheet::GetSheetWidth(BOOL bAsPaperUnit) const { double nWidth = 0.0; int nColNum = m_columns.Length(); for (int i = 0; i < nColNum; i++) { const SheetColumn &column = m_columns[i]; nWidth += column.m_nWidth; } if (!bAsPaperUnit) { double nScale = GetPScale(); nWidth *= nScale; } return nWidth; } // 取得连续几行的行高 double CDbSheet::GetRowsHeight(int nRowFrom, int nRowTo, BOOL bAsPaperUnit) const { double nHeight = 0.0; for (int i = nRowFrom; i <= nRowTo; i++) { nHeight += GetRowHeight(i, bAsPaperUnit); } return nHeight; } //取得连续几列的列宽 double CDbSheet::GetColumnsWidth(int nColFrom, int nColTo, BOOL bAsPaperUnit) const { double nWidth = 0.0; for (int i = nColFrom; i <= nColTo; i++) { nWidth += GetColumnWidth(i, bAsPaperUnit); } return nWidth; } // 得到某一行的高度 double CDbSheet::GetRowHeight(int nRow, BOOL bAsPaperUnit) const { ASSERT(nRow < m_rows.Length()); if (nRow >= m_rows.Length()) return 0.0; const SheetRow &row = m_rows[nRow]; double nHeight = 0.0; if (row.m_nHeightFlag == SheetRow::kParent && m_rowHeightStyle == SheetRow::kFixed) nHeight = m_nRowHeight; else nHeight = row.m_nHeight; if (!bAsPaperUnit) nHeight *= GetPScale(); return nHeight; } // 取得某列的宽度 double CDbSheet::GetColumnWidth(int nCol, BOOL bAsPaperUnit) const { ASSERT(nCol < m_columns.Length()); const SheetColumn &column = m_columns[nCol]; double nWidth = column.m_nWidth; if (!bAsPaperUnit) nWidth *= GetPScale(); return nWidth; } // 取得某列的左上角点 XPoint CDbSheet::GetColumnPoint(int nCol) const { XPoint ptTopLeft = GetTopLeft(FALSE); double nWidth = GetColumnsWidth(0, nCol - 1, FALSE); ads_polar(XPoint(ptTopLeft), Layout2Wcs(m_nRotation), nWidth, ptTopLeft); return ptTopLeft; } // 取得某行的左上角点 XPoint CDbSheet::GetRowPoint(int nRow) const { XPoint ptTopLeft = GetTopLeft(FALSE); double nHeight = GetRowsHeight(0, nRow - 1, FALSE); ads_polar(XPoint(ptTopLeft), Layout2Wcs(m_nRotation) - PI / 2, nHeight, ptTopLeft); return ptTopLeft; } //取的表格的左上角点 XPoint CDbSheet::GetTopLeft(BOOL bIncludeTitle) const { XPoint ext = GetExtents(bIncludeTitle, FALSE); XPoint ptLowLeft = Align2Base(GetLocation(), GetExtents(m_title.IsVisible(), FALSE)); XPoint ptTopLeft; ads_polar(ptLowLeft, Layout2Wcs(m_nRotation) + PI / 2, ext.y, ptTopLeft); return ptTopLeft; } // 取得表格位置 XPoint CDbSheet::GetLocation() const { return m_ptLocation; } // 取表格旋转角度 double CDbSheet::GetRotation() const { return m_nRotation; } // 取表格定位方式 AcGiDraw::TextAlignment CDbSheet::GetAlignment() const { return m_nAlignment; } //取缺省的行高 double CDbSheet::GetRowHeight(BOOL bAsPaperUnit) const { double h = m_nRowHeight; if (!bAsPaperUnit) h *= GetPScale(); return h; } // 设置表格位置 void CDbSheet::SetLocation(XPoint pt) { assertWriteEnabled(); m_ptLocation = pt; m_ptLocation.z = 0; } // 设置表格转角 void CDbSheet::SetRotation(double nRot) { assertWriteEnabled(); m_nRotation = nRot; } // 设置表格的定位对齐方式 void CDbSheet::SetAlignment(AcGiDraw::TextAlignment nAlign) { assertWriteEnabled(); m_nAlignment = nAlign; } //设置缺省的行高 void CDbSheet::SetRowHeight(double h, BOOL bAsPaperUnit) { assertWriteEnabled(); m_nRowHeight = h; if (!bAsPaperUnit) m_nRowHeight /= GetPScale(); } ////////////////////////////////////////////////////////////////// // 单元格属性 XPoint CDbSheet::GetCellSize(int nRow, int nCol, BOOL bAsPaperUnit) const { const GridCell &cell = *(*this)(nRow, nCol); double w, h; if (cell.IsRange()) { const GridRange &range = *cell.GetRange(); w = GetColumnsWidth(range.m_nColumn, range.m_nColumnMax, bAsPaperUnit); h = GetRowsHeight(range.m_nRow, range.m_nRowMax, bAsPaperUnit); } else { w = GetColumnWidth(nCol, bAsPaperUnit); h = GetRowHeight(nRow, bAsPaperUnit); } return XPoint(w, h); } XPoint CDbSheet::GetCellPoint(int nRow, int nCol) const { const GridCell *pCell = (*this)(nRow, nCol); if (pCell->IsRange()) { nRow = pCell->GetRange()->GetCoord(TRUE); nCol = pCell->GetRange()->GetCoord(FALSE); } double x = GetColumnsWidth(0, nCol - 1, FALSE); double y = GetRowsHeight(0, nRow - 1, FALSE); XPoint ptTopLeft = GetTopLeft(FALSE); XPoint ptDest; ads_polar(ptTopLeft, Layout2Wcs(m_nRotation), x, ptDest); ads_polar(XPoint(ptDest), Layout2Wcs(m_nRotation) - PI / 2, y, ptDest); return ptDest; } // 判断某单元格是否有底线 BOOL CDbSheet::HasRowDivider(int nRow, int nCol) const { const GridCell *pCell = (*this)(nRow, nCol); if (!pCell) return TRUE; //没有内容的单元格, 作为空的单元格, 有底线 BOOL bRet = TRUE; if (pCell->IsRange() && nRow < pCell->GetRange()->m_nRowMax) bRet = FALSE; return bRet; } // 判断某单元格是否有右线 BOOL CDbSheet::HasColumnDivider(int nRow, int nCol) const { const GridCell *pCell = (*this)(nRow, nCol); if (!pCell) //没有内容的单元格, 作为空的单元格, 有边线 return TRUE; BOOL bRet = TRUE; if (pCell->IsRange() && nCol < pCell->GetRange()->m_nColumnMax) bRet = FALSE; return bRet; } // 求单元格最终有效的属性样式 const GridStyle * CDbSheet::GetCellGridStyle(int nRow, int nCol, int nOverFlag, BOOL *bLocal) const { const GridCell &cell = *(*this)(nRow, nCol); const GridStyle &rStyle = cell.IsRange() ? cell.GetRange()->m_gridStyle : cell.m_gridStyle; return GetCellGridStyle(rStyle, nCol, nOverFlag, bLocal); } // 取得单元格最终的有效样式 const GridStyle * CDbSheet::GetCellGridStyle(const GridStyle &rStyle, int nCol, int nOverFlag, BOOL*bLocal) const { const GridStyle *pGridStyle = NULL; if (rStyle.m_nOverride & nOverFlag) { pGridStyle = &rStyle; if (bLocal) *bLocal = TRUE; } else { if (bLocal) *bLocal = FALSE; const SheetColumn &column = m_columns[nCol]; if (column.m_gridStyle.m_nOverride & nOverFlag) pGridStyle = &column.m_gridStyle; else if (m_gridStyle.m_nOverride & nOverFlag) pGridStyle = &m_gridStyle; } return pGridStyle; } // 取得单元格的水平对齐方式 AcDb::TextHorzMode CDbSheet::GetCellHorMode(int nRow, int nCol, BOOL *bLocal) const { const GridStyle *style = GetCellGridStyle(nRow, nCol, OF_HORMODE, bLocal); ASSERT(style); return style->m_nHorMode; } // 取得单元格的垂直对齐方式, 继承方式不同于其它 AcDb::TextVertMode CDbSheet::GetCellVerMode(int nRow, int nCol, BOOL *bLocal) const { const GridCell &cell = *(*this)(nRow, nCol); const GridStyle &rStyle = cell.IsRange() ? cell.GetRange()->m_gridStyle : cell.m_gridStyle; AcDb::TextVertMode nVerMode; if (rStyle.m_nOverride & OF_VERMODE) { nVerMode = rStyle.m_nVerMode; if (bLocal) *bLocal = TRUE; } else { nVerMode = m_rows[nRow].m_nVerMode; if (nVerMode == AcDb::kTextBase) { //继承 nVerMode = m_gridStyle.GetVerMode(); } if (bLocal) *bLocal = FALSE; } return nVerMode; } //取得单元格的文本行间距 double CDbSheet::GetCellLineSpace(int nRow, int nCol, BOOL bAsPaperUnit) const { const GridStyle *style1 = GetCellGridStyle(nRow, nCol, OF_LINESPACE); const GridStyle *style2 = GetCellGridStyle(nRow, nCol, OF_TEXTHEIGHT); ASSERT(style1 && style2); double nVal = style1->m_nLineSpaceFactor * style2->m_nTextHeight; if (!bAsPaperUnit) nVal *= GetPScale(); return nVal; } //取得单元格的文本行间距 double CDbSheet::GetCellLineSpaceFactor(int nRow, int nCol, BOOL *bLocal) const { const GridStyle *style = GetCellGridStyle(nRow, nCol, OF_LINESPACE, bLocal); ASSERT(style); double nLineSpaceFactor = style->m_nLineSpaceFactor; return nLineSpaceFactor; } // 取得单元格的文本高度 double CDbSheet::GetCellTextHeight(int nRow, int nCol, BOOL bAsPaperUnit, BOOL *bLocal) const { const GridStyle *style = GetCellGridStyle(nRow, nCol, OF_TEXTHEIGHT, bLocal); ASSERT(style); double nHeight = style->m_nTextHeight; if (!bAsPaperUnit) nHeight *= GetPScale(); return nHeight; } // 取得单元格的文字样式 AcDbObjectId CDbSheet::GetCellTextStyle(int nRow, int nCol, BOOL *bLocal) const { const GridStyle *style = GetCellGridStyle(nRow, nCol, OF_TEXTSTYLE, bLocal); ASSERT(style); AcDbObjectId idStyle = style->m_idTextStyle; if (!idStyle) idStyle = m_gridStyle.GetTextStyleId(); return idStyle; } // 取得单元格的文字颜色 Adesk::UInt16 CDbSheet::GetCellTextColor(int nRow, int nCol, BOOL *bLocal) const { const GridStyle *style = GetCellGridStyle(nRow, nCol, OF_TEXTCOLOR, bLocal); ASSERT(style); return style->m_nTextColor; } // 单元格文字是否自动换行 BOOL CDbSheet::IsCellWrapEnabled(int nRow, int nCol, BOOL *bLocal) const { const GridStyle *style = GetCellGridStyle(nRow, nCol, OF_TEXTWRAP, bLocal); ASSERT(style); return style->m_bTextWrap; } ////////////////////////////////////////////////////////////////// // 标题的属性 // 标题的属性为局部, 不继承 // 求标题最终有效的属性样式 const GridStyle * CDbSheet::GetTitleGridStyle(int nOverFlag, BOOL *bLocal) const { const GridStyle *pGridStyle = NULL; pGridStyle = &m_title.m_gridStyle; if (bLocal) *bLocal = TRUE; /* if(m_title.m_gridStyle.m_nOverride&nOverFlag) { pGridStyle=&m_title.m_gridStyle; if(bLocal) *bLocal=TRUE; } else if(m_gridStyle.m_nOverride&nOverFlag) { pGridStyle=&m_gridStyle; if(bLocal) *bLocal=FALSE; }*/ return pGridStyle; } // 标题的高度 double CDbSheet::GetTitleHeight(BOOL bAsPaperUnit) const { double nHeight = m_title.m_nHeight; if (!bAsPaperUnit) nHeight *= GetPScale(); return nHeight; } // 标题文字的水平对齐方式 AcDb::TextHorzMode CDbSheet::GetTitleHorMode(BOOL *bLocal) const { const GridStyle *style = GetTitleGridStyle(OF_HORMODE, bLocal); ASSERT(style); return style->m_nHorMode; } // 取得单元格的垂直对齐方式 AcDb::TextVertMode CDbSheet::GetTitleVerMode(BOOL *bLocal) const { const GridStyle *style = GetTitleGridStyle(OF_VERMODE, bLocal); ASSERT(style); return style->GetVerMode(); } // 标题的文字行间距 double CDbSheet::GetTitleLineSpace(BOOL bAsPaperUnit) const { double nTextHeight = GetTitleTextHeight(bAsPaperUnit); const GridStyle *style = GetTitleGridStyle(OF_LINESPACE); double nLineSpaceFactor = (style ? style->m_nLineSpaceFactor : LSF_DEFAULT); return (nTextHeight * nLineSpaceFactor); } // 标题的文字行间距 double CDbSheet::GetTitleLineSpaceFactor(BOOL *bLocal) const { const GridStyle *style = GetTitleGridStyle(OF_LINESPACE, bLocal); double nLineSpaceFactor = (style ? style->m_nLineSpaceFactor : LSF_DEFAULT); return nLineSpaceFactor; } // 标题的文字高度 double CDbSheet::GetTitleTextHeight(BOOL bAsPaperUnit, BOOL *bLocal) const { const GridStyle *style = GetTitleGridStyle(OF_TEXTHEIGHT, bLocal); ASSERT(style); double nHeight = style->m_nTextHeight; if (!bAsPaperUnit) nHeight *= GetPScale(); return nHeight; } // 标题的文字样式 AcDbObjectId CDbSheet::GetTitleTextStyle(BOOL *bLocal) const { const GridStyle *style = GetTitleGridStyle(OF_TEXTSTYLE, bLocal); ASSERT(style); AcDbObjectId idStyle = style->m_idTextStyle; if (!idStyle) idStyle = m_gridStyle.GetTextStyleId(); return idStyle; } Adesk::UInt16 CDbSheet::GetTitleTextColor(BOOL *bLocal) const { const GridStyle *style = GetTitleGridStyle(OF_TEXTCOLOR, bLocal); ASSERT(style); return style->GetTextColor(); } // 标题文字是否自动换行 BOOL CDbSheet::IsTitleWrapEnabled(BOOL *bLocal) const { const GridStyle *style = GetTitleGridStyle(OF_TEXTWRAP, bLocal); ASSERT(style); return style->m_bTextWrap; } // 取得标题文本 const TCHAR *CDbSheet::GetTitleText() const { return (const TCHAR *)m_title.m_sText; } // 设置标题文本 void CDbSheet::SetTitleText(const TCHAR *szText) { assertWriteEnabled(); m_title.m_sText = szText; } void CDbSheet::SetTitleHeight(double h, BOOL bAsPaperUnit) { assertWriteEnabled(); if (!bAsPaperUnit) h /= GetPScale(); m_title.SetHeight(h); } void CDbSheet::SetTitleGridStyle(const GridStyle &gridStyle) { assertWriteEnabled(); m_title.SetGridStyle(gridStyle); } const SheetTitle & CDbSheet::GetTitle() const { return m_title; } SheetTitle& CDbSheet::GetTitle() { return m_title; } const TCHAR* CDbSheet::GetDefaultLayer()const { return LAY_SHEET; } void InitDbSheet(BOOL bTrue) { if (bTrue) { CDbSheet::rxInit(); acrxBuildClassHierarchy(); //CDbSheet::InitMatchProtocol(TRUE); } else { //CDbSheet::InitMatchProtocol(FALSE); deleteAcRxClass(CDbSheet::desc()); } }