home *** CD-ROM | disk | FTP | other *** search
/ C Programming Starter Kit 2.0 / SamsPublishing-CProgrammingStarterKit-v2.0-Win31.iso / bc45 / step16.pak / STEP16DV.CPP < prev    next >
C/C++ Source or Header  |  1997-07-23  |  17KB  |  755 lines

  1. //----------------------------------------------------------------------------
  2. // ObjectWindows - (C) Copyright 1994 by Borland International
  3. //   Tutorial application -- step16dv.cpp
  4. //   Automation Server example
  5. //----------------------------------------------------------------------------
  6. #include <owl/owlpch.h>
  7. #include <owl/dc.h>
  8. #include <owl/inputdia.h>
  9. #include <owl/chooseco.h>
  10. #include <owl/gdiobjec.h>
  11. #include <owl/docmanag.h>
  12. #include <owl/listbox.h>
  13. #include <owl/controlb.h>
  14. #include <owl/buttonga.h>
  15. #include <classlib/arrays.h>
  16. #include <owl/olemdifr.h>
  17. #include <owl/oledoc.h>
  18. #include <owl/oleview.h>
  19. #include <ocf/automacr.h>
  20. #include "step16dv.h"
  21. #include "step16.h"
  22. #include "step16dv.rc"
  23.  
  24. BEGIN_REGISTRATION(DocReg)
  25.   REGDATA(progid,     "DrawPad.Drawing.16")
  26.   REGDATA(description,"DrawPad (Step16--AutoServer) Drawing")
  27.   REGDATA(menuname,   "Drawing")
  28.   REGDATA(extension,  "p16")
  29.   REGDATA(docfilter,  "*.p16")
  30.   REGDOCFLAGS(dtAutoOpen | dtAutoDelete | dtUpdateDir | dtCreatePrompt | dtRegisterExt)
  31. //REGDATA(debugger,   "tdw")
  32.   REGDATA(insertable, "")
  33.   REGDATA(verb0,      "&Edit")
  34.   REGDATA(verb1,      "&Open")
  35.   REGFORMAT(0, ocrEmbedSource,  ocrContent,  ocrIStorage,  ocrSet)
  36.   REGFORMAT(1, ocrMetafilePict, ocrContent,  ocrMfPict|ocrStaticMed, ocrGet)
  37. END_REGISTRATION
  38. BEGIN_REGISTRATION(ListReg)
  39.   REGDATA(description,"Line List")
  40.   REGDATA(extension,  "p16")
  41.   REGDATA(docfilter,  "*.p16")
  42.   REGDOCFLAGS(dtAutoDelete | dtHidden)
  43. END_REGISTRATION
  44.  
  45. DEFINE_DOC_TEMPLATE_CLASS(TDrawDocument, TDrawView,       DrawTemplate);
  46. DEFINE_DOC_TEMPLATE_CLASS(TDrawDocument, TDrawListView,   DrawListTemplate);
  47. DrawTemplate drawTpl(DocReg);
  48. DrawListTemplate drawListTpl(ListReg);
  49.  
  50. //===============================  TLine  =====================================
  51. //
  52. void
  53. TLine::SetPen(int penSize)
  54. {
  55.   if (penSize < 1)
  56.     PenSize = 1;
  57.   else
  58.     PenSize = penSize;
  59. }
  60.  
  61. void
  62. TLine::SetPen(TColor& newColor, int penSize)
  63. {
  64.   // If penSize isn't the default (0), set PenSize to the new size.
  65.   if (penSize)
  66.     PenSize = penSize;
  67.  
  68.   Color = newColor;
  69. }
  70.  
  71. bool
  72. TLine::Draw(TDC& dc) const
  73. {
  74.   // Set pen for the dc to the values for this line
  75.   TPen pen(Color, PenSize, PS_INSIDEFRAME);
  76.   dc.SelectObject(pen);
  77.  
  78.   // Iterates through the points in the line i.
  79.   TPointsIterator j(*this);
  80.   bool first = true;
  81.  
  82.   while (j) {
  83.     TPoint p = j++;
  84.  
  85.     if (!first)
  86.       dc.LineTo(p);
  87.     else {
  88.       dc.MoveTo(p);
  89.       first = false;
  90.     }
  91.   }
  92.   dc.RestorePen();
  93.   return true;
  94. }
  95.  
  96. ostream&
  97. operator <<(ostream& os, const TLine& line)
  98. {
  99.   // Write the number of points in the line
  100.   os << line.GetItemsInContainer();
  101.  
  102.   // Get and write pen attributes.
  103.   os << ' ' << line.Color << ' ' << line.PenSize;
  104.  
  105.   // Get an iterator for the array of points
  106.   TPointsIterator j(line);
  107.  
  108.   // While the iterator is valid (i.e. we haven't run out of points)
  109.   while(j)
  110.     // Write the point from the iterator and increment the array.
  111.     os << j++;
  112.   os << '\n';
  113.  
  114.   // return the stream object
  115.   return os;
  116. }
  117.  
  118. istream&
  119. operator >>(istream& is, TLine& line)
  120. {
  121.   unsigned numPoints;
  122.   is >> numPoints;
  123.  
  124.   COLORREF color;
  125.   int penSize;
  126.   is >> color >> penSize;
  127.   line.SetPen(TColor(color), penSize);
  128.  
  129.   while (numPoints--) {
  130.     TPoint point;
  131.     is >> point;
  132.     line.Add(point);
  133.   }
  134.  
  135.   // return the stream object
  136.   return is;
  137. }
  138.  
  139. DEFINE_AUTOCLASS(TDrawDocument)
  140.   EXPOSE_PROPRW(PenSize,    TAutoShort, "PenSize",    "Current pen size", 0)
  141.   EXPOSE_PROPRW(PenColor,   TAutoLong,  "PenColor",   "Current pen color", 0)
  142.   EXPOSE_METHOD(AddPoint,   TAutoVoid,  "AddPoint",   "Add a point to the current line", 0)
  143.    REQUIRED_ARG(            TAutoShort, "X")
  144.    REQUIRED_ARG(            TAutoShort, "Y")
  145.   EXPOSE_METHOD(AddLine,    TAutoVoid,  "AddLine",    "Add current line into drawing", 0)
  146.   EXPOSE_METHOD(ClearLine,  TAutoVoid,  "ClearLine",  "Erases current line", 0)
  147.   EXPOSE_APPLICATION(       TDrawApp,   "Application","Application object", 0)
  148. END_AUTOCLASS(TDrawDocument, tfNormal,  "TDrawDoc",   "Draw document class", 0)
  149.  
  150. TDrawDocument::TDrawDocument(TDocument* parent)
  151.   : TOleDocument(parent), UndoLine(0), UndoState(UndoNone)
  152. {
  153.   Lines         = new TLines(100, 0, 5);
  154.   AutoPenSize   = 1;
  155.   AutoPenColor  = RGB(0, 0, 0);
  156.   AutoLine      = new TLine(AutoPenColor, AutoPenSize);
  157. }
  158.  
  159. TDrawDocument::~TDrawDocument()
  160. {
  161.   delete AutoLine;
  162.   delete Lines;
  163.   delete UndoLine;
  164. }
  165.  
  166. bool
  167. TDrawDocument::Commit(bool force)
  168. {
  169.   TOleDocument::Commit(force);
  170.  
  171.   TOutStream* os = OutStream(ofWrite);
  172.   if (!os)
  173.     return false;
  174.  
  175.   // Write the number of lines in the figure
  176.   *os << Lines->GetItemsInContainer();
  177.  
  178.   // Append a description using a resource string
  179.   *os << ' ' << FileInfo << '\n';
  180.  
  181.   // Get an iterator for the array of lines
  182.   TLinesIterator i(*Lines);
  183.  
  184.   // While the iterator is valid (i.e. we haven't run out of lines)
  185.   while (i) {
  186.     // Copy the current line from the iterator and increment the array.
  187.     *os << i++;
  188.   }
  189.   delete os;
  190.  
  191.   //
  192.   // Commit the storage if it was opened in transacted mode
  193.   TOleDocument::CommitTransactedStorage();
  194.   SetDirty(false);
  195.  
  196.   return true;
  197. }
  198.  
  199. bool
  200. TDrawDocument::Open(int mode, const char far* path)
  201. {
  202.   char fileinfo[100];
  203.  
  204.   TOleDocument::Open(mode, path);
  205.   if (GetDocPath()) {
  206.     TInStream* is = (TInStream*)InStream(ofRead);
  207.     if (!is)
  208.       return false;
  209.  
  210.     unsigned numLines;
  211.     *is >> numLines;
  212.     is->getline(fileinfo, sizeof(fileinfo));
  213.     while (numLines--) {
  214.       TLine line;
  215.       *is >> line;
  216.       Lines->Add(line);
  217.     }
  218.  
  219.     delete is;
  220.  
  221.     FileInfo = fileinfo;
  222.   } else {
  223.     FileInfo = string(*::Module,IDS_FILEINFO);
  224.   }
  225.   SetDirty(false);
  226.   UndoState = UndoNone;
  227.   return true;
  228. }
  229.  
  230. bool
  231. TDrawDocument::Close()
  232. {
  233.   if (TOleDocument::Close()) {
  234.     Lines->Flush();
  235.     return true;
  236.   }
  237.  
  238.   return false;
  239. }
  240.  
  241. TLine*
  242. TDrawDocument::GetLine(uint index)
  243. {
  244.   return index < Lines->GetItemsInContainer() ? &(*Lines)[index] : 0;
  245. }
  246.  
  247. int
  248. TDrawDocument::AddLine(TLine& line)
  249. {
  250.   int index = Lines->GetItemsInContainer();
  251.   Lines->Add(line);
  252.   SetDirty(true);
  253.   NotifyViews(vnDrawAppend, index);
  254.   UndoState = UndoAppend;
  255.   return index;
  256. }
  257.  
  258. void
  259. TDrawDocument::DeleteLine(uint index)
  260. {
  261.   const TLine* oldLine = GetLine(index);
  262.   if (!oldLine)
  263.     return;
  264.   delete UndoLine;
  265.   UndoLine = new TLine(*oldLine);
  266.   Lines->Detach(index);
  267.   SetDirty(true);
  268.   NotifyViews(vnDrawDelete, index);
  269.   UndoState = UndoDelete;
  270. }
  271.  
  272. void
  273. TDrawDocument::ModifyLine(TLine& line, uint index)
  274. {
  275.   delete UndoLine;
  276.   UndoLine = new TLine((*Lines)[index]);
  277.   SetDirty(true);
  278.   (*Lines)[index] = line;
  279.   NotifyViews(vnDrawModify, index);
  280.   UndoState = UndoModify;
  281.   UndoIndex = index;
  282. }
  283.  
  284. void
  285. TDrawDocument::Clear()
  286. {
  287.   Lines->Flush();
  288.   NotifyViews(vnRevert, true);
  289. }
  290.  
  291. void
  292. TDrawDocument::Undo()
  293. {
  294.   switch (UndoState) {
  295.     case UndoAppend:
  296.       DeleteLine(Lines->GetItemsInContainer()-1);
  297.       return;
  298.     case UndoDelete:
  299.       AddLine(*UndoLine);
  300.       delete UndoLine;
  301.       UndoLine = 0;
  302.       return;
  303.     case UndoModify:
  304.       TLine* temp = UndoLine;
  305.       UndoLine = 0;
  306.       ModifyLine(*temp, UndoIndex);
  307.       delete temp;
  308.   }
  309. }
  310.  
  311. bool
  312. GetPenSize(TWindow* parent, TLine& line)
  313. {
  314.   char inputText[6];
  315.  
  316.   wsprintf(inputText, "%d", line.PenSize);
  317.   if (TInputDialog(parent, "Line Thickness",
  318.                    "Input a new thickness:",
  319.                    inputText,
  320.                    sizeof(inputText)).Execute() != IDOK)
  321.     return false;
  322.   line.PenSize = atoi(inputText);
  323.  
  324.   if (line.PenSize < 1)
  325.     line.PenSize = 1;
  326.  
  327.   return true;
  328. }
  329.  
  330. bool
  331. GetPenColor(TWindow* parent, TLine& line)
  332. {
  333.   TChooseColorDialog::TData colors;
  334.   static TColor custColors[16] =
  335.   {
  336.     0x010101L, 0x101010L, 0x202020L, 0x303030L,
  337.     0x404040L, 0x505050L, 0x606060L, 0x707070L,
  338.     0x808080L, 0x909090L, 0xA0A0A0L, 0xB0B0B0L,
  339.     0xC0C0C0L, 0xD0D0D0L, 0xE0E0E0L, 0xF0F0F0L
  340.   };
  341.  
  342.   colors.Flags = CC_RGBINIT;
  343.   colors.Color = TColor(line.QueryColor());
  344.   colors.CustColors = custColors;
  345.   if (TChooseColorDialog(parent, colors).Execute() != IDOK)
  346.     return false;
  347.   line.SetPen(colors.Color);
  348.   return true;
  349. }
  350.  
  351. DEFINE_RESPONSE_TABLE1(TDrawView, TOleView)
  352.   EV_WM_LBUTTONDOWN,
  353.   EV_WM_MOUSEMOVE,
  354.   EV_WM_LBUTTONUP,
  355.   EV_COMMAND(CM_PENSIZE, CmPenSize),
  356.   EV_COMMAND(CM_PENCOLOR, CmPenColor),
  357.   EV_COMMAND(CM_EDITCLEAR, CmClear),
  358.   EV_COMMAND(CM_EDITUNDO, CmUndo),
  359.   EV_VN_COMMIT,
  360.   EV_VN_REVERT,
  361.   EV_VN_DRAWAPPEND,
  362.   EV_VN_DRAWDELETE,
  363.   EV_VN_DRAWMODIFY,
  364.   EV_OC_VIEWPARTSIZE,
  365.   EV_OC_VIEWSHOWTOOLS,
  366. END_RESPONSE_TABLE;
  367.  
  368. TDrawView::TDrawView(TDrawDocument& doc, TWindow* parent)
  369. :
  370.   TOleView(doc, parent), DrawDoc(&doc)
  371. {
  372.   Line      = new TLine(TColor::Black, 1);
  373.   Attr.AccelTable = IDA_DRAWVIEW;
  374.   SetViewMenu(new TMenuDescr(IDM_DRAWVIEW));
  375.   ToolBar = 0;
  376. }
  377.  
  378. //
  379. // Let container know about the server view size in pixels
  380. //
  381. bool
  382. TDrawView::EvOcViewPartSize(TOcPartSize far& ps)
  383. {
  384.   TClientDC dc(*this);
  385.  
  386.   TRect rect(0, 0, 0, 0);
  387.   // a 2" x 2" extent for server
  388.   //
  389.   rect.right  = dc.GetDeviceCaps(LOGPIXELSX) * 2;
  390.   rect.bottom = dc.GetDeviceCaps(LOGPIXELSY) * 2;
  391.  
  392.   ps.PartRect = rect;
  393.   return true;
  394. }
  395.  
  396. bool
  397. TDrawView::EvOcViewShowTools(TOcToolBarInfo far& tbi)
  398. {
  399.   // Construct & create a control bar for show, destroy our bar for hide
  400.   //
  401.   if (tbi.Show) {
  402.     if (!ToolBar) {
  403.       ToolBar = new TControlBar(this);
  404.       ToolBar->Insert(*new TButtonGadget(CM_PENSIZE, CM_PENSIZE, TButtonGadget::Command));
  405.       ToolBar->Insert(*new TButtonGadget(CM_PENCOLOR, CM_PENCOLOR, TButtonGadget::Command));
  406.       ToolBar->Insert(*new TSeparatorGadget);
  407.       ToolBar->Insert(*new TButtonGadget(CM_ABOUT, CM_ABOUT, TButtonGadget::Command));
  408.       ToolBar->SetHintMode(TGadgetWindow::EnterHints);
  409.     }
  410.     ToolBar->Create();
  411.     tbi.HTopTB = (HWND)*ToolBar;
  412.   }
  413.   else {
  414.     if (ToolBar) {
  415.       ToolBar->Destroy();
  416.       delete ToolBar;
  417.       ToolBar = 0;
  418.     }
  419.   }
  420.   return true;
  421. }
  422.  
  423. void
  424. TDrawView::EvLButtonDown(uint modKeys, TPoint& point)
  425. {
  426.   TOleView::EvLButtonDown(modKeys, point);
  427.  
  428.   if (DragDC) {
  429.     SetCapture();
  430.     Pen = new TPen(Line->QueryColor(), Line->QueryPenSize());
  431.     DragDC->SelectObject(*Pen);
  432.     DragDC->MoveTo(point);
  433.     Line->Add(point);
  434.   }
  435. }
  436.  
  437. void
  438. TDrawView::EvMouseMove(uint modKeys, TPoint& point)
  439. {
  440.   TOleView::EvMouseMove(modKeys, point);
  441.  
  442.   if (DragDC) {
  443.     DragDC->LineTo(point);
  444.     Line->Add(point);
  445.   }
  446. }
  447.  
  448. void
  449. TDrawView::EvLButtonUp(uint modKeys, TPoint& point)
  450. {
  451.   if (DragDC) {
  452.     ReleaseCapture();
  453.     if (Line->GetItemsInContainer() > 1)
  454.       DrawDoc->AddLine(*Line);
  455.     Line->Flush();
  456.     delete Pen;
  457.   }
  458.  
  459.   TOleView::EvLButtonUp(modKeys, point);
  460. }
  461.  
  462. void
  463. TDrawView::CmPenSize()
  464. {
  465.   GetPenSize(this, *Line);
  466. }
  467.  
  468. void
  469. TDrawView::CmPenColor()
  470. {
  471.   GetPenColor(this, *Line);
  472. }
  473.  
  474. void
  475. TDrawView::CmClear()
  476. {
  477.   DrawDoc->Clear();
  478. }
  479.  
  480. void
  481. TDrawView::CmUndo()
  482. {
  483.   DrawDoc->Undo();
  484. }
  485.  
  486. //
  487. // Paint into the window dc
  488. //
  489. void
  490. TDrawView::Paint(TDC& dc, bool /*erase*/, TRect& /*rect*/)
  491. {
  492.   // Iterates through the array of line objects.
  493.   int j = 0;
  494.   TLine* line;
  495.   while ((line = const_cast<TLine *>(DrawDoc->GetLine(j++))) != 0)
  496.     line->Draw(dc);
  497. }
  498.  
  499. bool
  500. TDrawView::VnCommit(bool /*force*/)
  501. {
  502.   // nothing to do here, no data held in view
  503.   return true;
  504. }
  505.  
  506. bool
  507. TDrawView::VnRevert(bool /*clear*/)
  508. {
  509.   Invalidate();  // force full repaint
  510.   InvalidatePart(invView); // OC server change
  511.   return true;
  512. }
  513.  
  514. bool
  515. TDrawView::VnAppend(uint index)
  516. {
  517.   TClientDC dc(*this);
  518.   const TLine* line = DrawDoc->GetLine(index);
  519.   bool metafile = dc.GetDeviceCaps(TECHNOLOGY) == DT_METAFILE;
  520.   SetupDC(dc, !metafile);
  521.   line->Draw(dc);
  522.   InvalidatePart(invView);
  523.   return true;
  524. }
  525.  
  526. bool
  527. TDrawView::VnModify(uint /*index*/)
  528. {
  529.   Invalidate();  // force full repaint
  530.   InvalidatePart(invView); // OC server change
  531.   return true;
  532. }
  533.  
  534. bool
  535. TDrawView::VnDelete(uint /*index*/)
  536. {
  537.   Invalidate();  // force full repaint
  538.   InvalidatePart(invView); // OC server change
  539.   return true;
  540. }
  541.  
  542. DEFINE_RESPONSE_TABLE1(TDrawListView, TListBox)
  543.   EV_COMMAND(CM_PENSIZE, CmPenSize),
  544.   EV_COMMAND(CM_PENCOLOR, CmPenColor),
  545.   EV_COMMAND(CM_EDITCLEAR, CmClear),
  546.   EV_COMMAND(CM_EDITUNDO, CmUndo),
  547.   EV_COMMAND(CM_EDITDELETE, CmDelete),
  548.   EV_VN_ISWINDOW,
  549.   EV_VN_COMMIT,
  550.   EV_VN_REVERT,
  551.   EV_VN_DRAWAPPEND,
  552.   EV_VN_DRAWDELETE,
  553.   EV_VN_DRAWMODIFY,
  554. END_RESPONSE_TABLE;
  555.  
  556. TDrawListView::TDrawListView(TDrawDocument& doc,TWindow* parent)
  557.        : TView(doc), TListBox(parent, GetNextViewId(), 0,0,0,0), DrawDoc(&doc)
  558. {
  559.   Attr.Style &= ~(WS_BORDER | LBS_SORT);
  560.   Attr.Style |= LBS_NOINTEGRALHEIGHT;
  561.   Attr.AccelTable = IDA_DRAWLISTVIEW;
  562.   SetViewMenu(new TMenuDescr(IDM_DRAWLISTVIEW));
  563. }
  564.  
  565. bool
  566. TDrawListView::CanClose()
  567. {
  568.   TView* curView = Doc->GetViewList();
  569.   while (curView) {
  570.     if (curView != this)
  571.       return true;
  572.  
  573.     curView = curView->GetNextView();
  574.   }
  575.  
  576.   return Doc->CanClose();
  577. }
  578.  
  579. bool
  580. TDrawListView::Create()
  581. {
  582.   TListBox::Create();
  583.   LoadData();
  584.   return true;
  585. }
  586.  
  587. void
  588. TDrawListView::LoadData()
  589. {
  590.   ClearList();
  591.   int i = 0;
  592.   const TLine* line;
  593.   while ((line = DrawDoc->GetLine(i)) != 0)
  594.     FormatData(line, i++);
  595.  
  596.   SetSelIndex(0);
  597. }
  598.  
  599. void
  600. TDrawListView::FormatData(const TLine* line, int unsigned index)
  601. {
  602.   char buf[80];
  603.   TColor color(line->QueryColor());
  604.   wsprintf(buf, "Color = R%d G%d B%d, Size = %d, Points = %d",
  605.            color.Red(), color.Green(), color.Blue(),
  606.            line->QueryPenSize(), line->GetItemsInContainer());
  607.   DeleteString(index);
  608.   InsertString(buf, index);
  609.   SetSelIndex(index);
  610. }
  611.  
  612. void
  613. TDrawListView::CmPenSize()
  614. {
  615.   int index = GetSelIndex();
  616.   const TLine* line = DrawDoc->GetLine(index);
  617.   if (line) {
  618.     TLine* newline = new TLine(*line);
  619.     if (GetPenSize(this, *newline))
  620.       DrawDoc->ModifyLine(*newline, index);
  621.     delete newline;
  622.   }
  623. }
  624.  
  625. void
  626. TDrawListView::CmPenColor()
  627. {
  628.   int index = GetSelIndex();
  629.   const TLine* line = DrawDoc->GetLine(index);
  630.   if (line) {
  631.     TLine* newline = new TLine(*line);
  632.     if (GetPenColor(this, *newline))
  633.       DrawDoc->ModifyLine(*newline, index);
  634.     delete newline;
  635.   }
  636. }
  637.  
  638. void
  639. TDrawListView::CmClear()
  640. {
  641.   DrawDoc->Clear();
  642. }
  643.  
  644. void
  645. TDrawListView::CmUndo()
  646. {
  647.   DrawDoc->Undo();
  648. }
  649.  
  650. void
  651. TDrawListView::CmDelete()
  652. {
  653.   DrawDoc->DeleteLine(GetSelIndex());
  654. }
  655.  
  656. bool
  657. TDrawListView::VnCommit(bool /*force*/)
  658. {
  659.   return true;
  660. }
  661.  
  662. bool
  663. TDrawListView::VnRevert(bool /*clear*/)
  664. {
  665.   LoadData();
  666.   return true;
  667. }
  668.  
  669. bool
  670. TDrawListView::VnAppend(uint index)
  671. {
  672.   const TLine* line = DrawDoc->GetLine(index);
  673.   FormatData(line, index);
  674.   SetSelIndex(index);
  675.   return true;
  676. }
  677.  
  678. bool
  679. TDrawListView::VnDelete(uint index)
  680. {
  681.   DeleteString(index);
  682.   HandleMessage(WM_KEYDOWN,VK_DOWN); // force selection
  683.   return true;
  684. }
  685.  
  686. bool
  687. TDrawListView::VnModify(uint index)
  688. {
  689.   const TLine* line = DrawDoc->GetLine(index);
  690.   FormatData(line, index);
  691.   return true;
  692. }
  693.  
  694. static char* PropNames[] = {
  695.   "Line Count",      // LineCount
  696.   "Description",       // Description
  697. };
  698.  
  699. static int PropFlags[] = {
  700.   pfGetBinary|pfGetText, // LineCount
  701.   pfGetText,             // Description
  702. };
  703.  
  704. const char*
  705. TDrawDocument::PropertyName(int index)
  706. {
  707.   if (index <= PrevProperty)
  708.     return TStorageDocument::PropertyName(index);  // OC server change
  709.   else if (index < NextProperty)
  710.     return PropNames[index-PrevProperty-1];
  711.   else
  712.     return 0;
  713. }
  714.  
  715. int
  716. TDrawDocument::PropertyFlags(int index)
  717. {
  718.   if (index <= PrevProperty)
  719.     return TStorageDocument::PropertyFlags(index); // OC server change
  720.   else if (index < NextProperty)
  721.     return PropFlags[index-PrevProperty-1];
  722.   else
  723.     return 0;
  724. }
  725.  
  726. int
  727. TDrawDocument::FindProperty(const char far* name)
  728. {
  729.   for (int i=0; i < NextProperty-PrevProperty-1; i++)
  730.     if (strcmp(PropNames[i], name) == 0)
  731.       return i+PrevProperty+1;
  732.   return 0;
  733. }
  734.  
  735. int
  736. TDrawDocument::GetProperty(int prop, void far* dest, int textlen)
  737. {
  738.   switch(prop) {
  739.     case LineCount: {
  740.       int count = Lines->GetItemsInContainer();
  741.       if (!textlen) {
  742.         *(int far*)dest = count;
  743.         return sizeof(int);
  744.       }
  745.       return wsprintf((char far*)dest, "%d", count);
  746.     }
  747.     case Description:
  748.       char* temp = new char[textlen]; // need local copy for medium model
  749.       int len = FileInfo.copy(temp, textlen);
  750.       strcpy((char far*)dest, temp);
  751.       return len;
  752.   }
  753.   return TStorageDocument::GetProperty(prop, dest, textlen); // OC server change
  754. }
  755.