4.2.2.1. Управление текущим видом

Источник здесь.[перевод не проверен];[перевёл Андрей Бушман]

    Вы получаете доступ к текущему виду видового экрана пространства модели (Model space) или пространства листа (Paper space) посредством использования метода GetCurrentView (получить текущий вид) объекта Editor (редактор). Данный метод возвращает объект ViewTableRecord (запись таблицы видов). Вы используете объект ViewTableRecord для зуммирования, позиционирования и назначения ориентации вида в активном видовом экране. После того, как вы произведёте с объектом ViewTableRecord необходимые изменения, следует обновить текущий вид активного видового экрана посредством метода SetCurrentView (установить текущий вид).

    Далее приведены некоторые общие свойства, которые вы будете использовать для управления текущим видом:
  • CenterPoint (центральная точка) - Центральная точка вида в координатной системе отображения (DCS coordinates)1
  • Height (высота) - Высота вида в координатах DCS. Увеличение высоты приводит к удалению от объекта (zoom out); Уменьшение высоты приводит к приближению к объекту (zoom in).
  • Target (цель) - Целевая точка вида в WCS (мировая система координат)2.
  • ViewDirection (направление взгляда) - Вектор, направленный из целевой точки3 до камеры вида в WCS (мировая система координат).
  • ViewTwist (Угол наклона вида)- Угол наклона4 вида в радианах.
  • Width (ширина)- Ширина вида в координатах DCS. Увеличение ширины приводит к удалению от объекта (zoom out); Уменьшение ширины приводит к приближению к объекту (zoom in).

Перекрёстная ссылка на код VBA

    .NET API не предоставляет методов, непосредственно манипулирующих текущим видом чертежа подобно тем, которые имеются в библиотеке ActiveX. Напримет, если вы хотите зуммировать границы объектов в чертеже, или же получить границы чертежа, вам следует делать это посредством использования свойств Width (ширина), Height (высота) и CenterPoint (центральная точка) текущего вида.
Для получения границ или границ чертеже, вам следует использовать свойства Extmin, Extmax, Limmin, и Limmax объекта Database.

Функции управления текущим видом

    Пример этого кода является общей процедурой, которая используется в последующих примерах. Процедура Zoom (увеличение) принимает четыре параметра, чтобы достигнуть изменения масштаба изображения согласно границам, панорамирования или центрирования представления чертежа, и масштабирования представления чертежа в соответствии с переданными ей параметрам.

Параметрами процедуры зуммирования (Zoom) являются:
  • Minimum point (минимальная точка) - 3D точка, используемая для определения левого нижнего угла отображаемой площади.
  • Maximum point (максимальная точка) - 3D точка, используемая для определения правого верхнего угла отображаемой площади.
  • Center point (центральная точка)- 3D точка, указывающая центр вида.
  • Scale factor (масштабный коэффициент) - Действительное число, указывающее масштаб увеличения/уменьшения размеров вида.

Код VB.NET

   1:  Imports Autodesk.AutoCAD.ApplicationServices
   2:  Imports Autodesk.AutoCAD.DatabaseServices
   3:  Imports Autodesk.AutoCAD.Runtime
   4:  Imports Autodesk.AutoCAD.Geometry 
   5:   
   6:  Public Sub Zoom(ByVal pMin As Point3d, ByVal pMax As Point3d, _
   7:  ByVal pCenter As Point3d, ByVal dFactor As Double)
   8:   
   9:  '' Получаем текущий документ и его базу данных
  10:  Dim acDoc As Document = Application.DocumentManager.MdiActiveDocument
  11:  Dim acCurDb As Database = acDoc.Database
  12:  Dim nCurVport As Integer = System.Convert.ToInt32(Application.GetSystemVariable("CVPORT")) 
  13:   
  14:  '' Получаем границы текущего пространства, когда не задано ни одной точки, или задана
  15:  '' Только центральная точка
  16:   
  17:  '' проверяем, является ли пространство модели текущим.
  18:  If acCurDb.TileMode = True Then
  19:  If pMin.Equals(New Point3d()) = True And _
  20:  pMax.Equals(New Point3d()) = True Then
  21:  pMin = acCurDb.Extmin
  22:  pMax = acCurDb.Extmax
  23:  End If
  24:  Else
  25:   
  26:  '' Проверяем, является ли пространство листа текущим.
  27:  If nCurVport = 1 Then
  28:  If pMin.Equals(New Point3d()) = True And _
  29:  pMax.Equals(New Point3d()) = True Then
  30:  pMin = acCurDb.Pextmin
  31:  pMax = acCurDb.Pextmax
  32:  End If
  33:  Else
  34:   
  35:  '' Получаем границы пространства модели
  36:  If pMin.Equals(New Point3d()) = True And _
  37:  pMax.Equals(New Point3d()) = True Then
  38:  pMin = acCurDb.Extmin
  39:  pMax = acCurDb.Extmax
  40:  End If
  41:  End If
  42:  End If 
  43:   
  44:  '' Запускаем транзакцию
  45:  Using acTrans As Transaction = acCurDb.TransactionManager.StartTransaction()
  46:   
  47:  '' Получаем текущий вид
  48:  Using acView As ViewTableRecord = acDoc.Editor.GetCurrentView()
  49:  Dim eExtents As Extents3d
  50:   
  51:  '' Переводим систему координат WCS (международную систему координат) в DCS (систему координат отображения)
  52:  Dim matWCS2DCS As Matrix3d
  53:  matWCS2DCS = Matrix3d.PlaneToWorld(acView.ViewDirection)
  54:  matWCS2DCS = Matrix3d.Displacement(acView.Target - Point3d.Origin) * matWCS2DCS
  55:  matWCS2DCS = Matrix3d.Rotation(-acView.ViewTwist, _
  56:  acView.ViewDirection, _
  57:  acView.Target) * matWCS2DCS 
  58:   
  59:  '' Если центральная точка указана, определяем
  60:  '' минимальную и максимальную точку границ
  61:  '' для режимов Center (центр) и Scale (масштаб)
  62:   
  63:  If pCenter.DistanceTo(Point3d.Origin) <> 0 Then
  64:  pMin = New Point3d(pCenter.X - (acView.Width / 2), _
  65:  pCenter.Y - (acView.Height / 2), 0)
  66:   
  67:  pMax = New Point3d((acView.Width / 2) + pCenter.X, _
  68:  (acView.Height / 2) + pCenter.Y, 0)
  69:  End If 
  70:   
  71:  '' Создаём границы используя отрезок
  72:  Using acLine As Line = New Line(pMin, pMax)
  73:   
  74:  eExtents = New Extents3d(acLine.Bounds.Value.MinPoint, _
  75:  acLine.Bounds.Value.MaxPoint)
  76:  End Using 
  77:   
  78:  '' Вычисляем отношение ширины  текущего вида к его высоте
  79:  Dim dViewRatio As Double
  80:  dViewRatio = (acView.Width / acView.Height) 
  81:   
  82:  '' Изменяем границы вида
  83:  matWCS2DCS = matWCS2DCS.Inverse()
  84:  eExtents.TransformBy(matWCS2DCS) 
  85:   
  86:  Dim dWidth As Double
  87:  Dim dHeight As Double
  88:  Dim pNewCentPt As Point2d 
  89:   
  90:  '' Проверяем, что центральная точка была обеспечена(режимы Center (центр) и Scale(масштаб))
  91:  If pCenter.DistanceTo(Point3d.Origin) <> 0 Then
  92:  dWidth = acView.Width
  93:  dHeight = acView.Height 
  94:   
  95:  If dFactor = 0 Then
  96:  pCenter = pCenter.TransformBy(matWCS2DCS)
  97:  End If 
  98:   
  99:  pNewCentPt = New Point2d(pCenter.X, pCenter.Y)
 100:   
 101:  Else 
 102:  '' Работа в окне, в режимах Extents (границы) и Limits (лимиты)
 103:  '' Вычисляем новую ширину и высоту текущего вида
 104:   
 105:  dWidth = eExtents.MaxPoint.X - eExtents.MinPoint.X
 106:  dHeight = eExtents.MaxPoint.Y - eExtents.MinPoint.Y 
 107:   
 108:  '' Получаем центральную точку вида
 109:  pNewCentPt = New Point2d(((eExtents.MaxPoint.X + eExtents.MinPoint.X) * 0.5), _
 110:  ((eExtents.MaxPoint.Y + eExtents.MinPoint.Y) * 0.5))
 111:  End If 
 112:   
 113:  '' Проверяем, вписывается ли новая ширина в текущее окно
 114:  If dWidth > (dHeight * dViewRatio) Then dHeight = dWidth / dViewRatio 
 115:   
 116:  '' Изменяем размеры и масштабируем вид
 117:  If dFactor <> 0 Then
 118:  acView.Height = dHeight * dFactor
 119:  acView.Width = dWidth * dFactor
 120:  End If 
 121:   
 122:  '' Устанавливаем центральную точку вида
 123:  acView.CenterPoint = pNewCentPt 
 124:   
 125:  '' Устанавливаем вид текущим
 126:  acDoc.Editor.SetCurrentView(acView)
 127:  End Using 
 128:   
 129:  '' Завершаем изменения
 130:  acTrans.Commit()
 131:  End Using
 132:  End Sub

Код C#

   1:  using Autodesk.AutoCAD.ApplicationServices;
   2:  using Autodesk.AutoCAD.DatabaseServices;
   3:  using Autodesk.AutoCAD.Runtime;
   4:  using Autodesk.AutoCAD.Geometry; 
   5:   
   6:  static void Zoom(Point3d pMin, Point3d pMax, Point3d pCenter, double dFactor)
   7:  {
   8:    // Получаем текущий документ и его базу данных
   9:    Document acDoc = Application.DocumentManager.MdiActiveDocument;
  10:    Database acCurDb = acDoc.Database; 
  11:   
  12:    int nCurVport = System.Convert.ToInt32(Application.GetSystemVariable("CVPORT")); 
  13:   
  14:    // Получаем границы текущего пространства без использования точек 
  15:    // или только по указанной центральной точке [прим. переводчика: сомневаюсь в правильности перевода, т.к. не понял смысла переведённого]
  16:    // Проверяем, является ли пространство модели текущим
  17:    if (acCurDb.TileMode == true)
  18:    {
  19:        if (pMin.Equals(new Point3d()) == true && 
  20:            pMax.Equals(new Point3d()) == true)
  21:        {
  22:            pMin = acCurDb.Extmin;
  23:            pMax = acCurDb.Extmax;
  24:        }
  25:    }
  26:    else
  27:    {
  28:        // Проверяем, является ли пространство листа текущим
  29:        if (nCurVport == 1)
  30:        {
  31:        // Получаем границы пространства листа
  32:            if (pMin.Equals(new Point3d()) == true && 
  33:                pMax.Equals(new Point3d()) == true)
  34:            {
  35:                pMin = acCurDb.Pextmin;
  36:                pMax = acCurDb.Pextmax;
  37:            }
  38:        }
  39:        else
  40:        {
  41:        // Получаем границы пространства модели
  42:            if (pMin.Equals(new Point3d()) == true && 
  43:                pMax.Equals(new Point3d()) == true)
  44:            {
  45:                pMin = acCurDb.Extmin;
  46:                pMax = acCurDb.Extmax;
  47:            }
  48:        }
  49:    }
  50:   
  51:      // Запускаем транзакцию
  52:    using (Transaction acTrans = acCurDb.TransactionManager.StartTransaction())
  53:    {
  54:      // Получаем текущий вид
  55:        using (ViewTableRecord acView = acDoc.Editor.GetCurrentView())
  56:        {
  57:            Extents3d eExtents;
  58:   
  59:      // Преобразовываем систему координат WCS в DCS
  60:            Matrix3d matWCS2DCS;
  61:            matWCS2DCS = Matrix3d.PlaneToWorld(acView.ViewDirection);
  62:            matWCS2DCS = Matrix3d.Displacement(acView.Target - Point3d.Origin) * matWCS2DCS;
  63:            matWCS2DCS = Matrix3d.Rotation(-acView.ViewTwist,
  64:                                           acView.ViewDirection,
  65:                                           acView.Target) * matWCS2DCS; 
  66:   
  67:      // Если центральная точка указана, определяем min и max 
  68:      // точку границы
  69:      // для режимов Center (центр) и Scale (масштаб)
  70:            if (pCenter.DistanceTo(Point3d.Origin) != 0)
  71:            {
  72:                pMin = new Point3d(pCenter.X - (acView.Width / 2),
  73:                                   pCenter.Y - (acView.Height / 2), 0);
  74:                pMax = new Point3d((acView.Width / 2) + pCenter.X,
  75:                                   (acView.Height / 2) + pCenter.Y, 0);
  76:            } 
  77:   
  78:      // Создание границы,посредством использования отрезка
  79:            using (Line acLine = new Line(pMin, pMax))
  80:            {
  81:                eExtents = new Extents3d(acLine.Bounds.Value.MinPoint,
  82:                                         acLine.Bounds.Value.MaxPoint);
  83:            } 
  84:   
  85:      // Вычисление отношения ширины текущего видового экрана к его высоте
  86:            double dViewRatio;
  87:            dViewRatio = (acView.Width / acView.Height); 
  88:   
  89:      // Преобразование границ вида
  90:            matWCS2DCS = matWCS2DCS.Inverse();
  91:            eExtents.TransformBy(matWCS2DCS); 
  92:   
  93:            double dWidth;
  94:            double dHeight;
  95:            Point2d pNewCentPt; 
  96:   
  97:      // Проверяем, обеспечена ли центральная точка (режимы Center и Scale)
  98:            if (pCenter.DistanceTo(Point3d.Origin) != 0)
  99:            {
 100:                dWidth = acView.Width;
 101:                dHeight = acView.Height; 
 102:   
 103:                if (dFactor == 0)
 104:                {
 105:                    pCenter = pCenter.TransformBy(matWCS2DCS);
 106:                }
 107:                pNewCentPt = new Point2d(pCenter.X, pCenter.Y);
 108:            }
 109:            else // Работаем в окне, режим Extents (границы) и  Limits (лимиты)
 110:            {
 111:                // Вычисляем новую ширину и высоту текущего вида
 112:                dWidth = eExtents.MaxPoint.X - eExtents.MinPoint.X;
 113:                dHeight = eExtents.MaxPoint.Y - eExtents.MinPoint.Y;
 114:   
 115:                // Определяем центральную точку вида
 116:                pNewCentPt = new Point2d(((eExtents.MaxPoint.X + eExtents.MinPoint.X) * 0.5),
 117:                                         ((eExtents.MaxPoint.Y + eExtents.MinPoint.Y) * 0.5));
 118:            } 
 119:   
 120:            // Проверяем, вписывается ли новая ширина в текущее окно
 121:            if (dWidth > (dHeight * dViewRatio)) dHeight = dWidth / dViewRatio; 
 122:   
 123:            // Изменяем размеры текущего вида и масштабируем его
 124:            if (dFactor != 0)
 125:            {
 126:                acView.Height = dHeight * dFactor;
 127:                acView.Width = dWidth * dFactor;
 128:            }
 129:   
 130:            // Устанавливаем центральную точку вида
 131:            acView.CenterPoint = pNewCentPt;
 132:   
 133:            // Устанавливаем вид текущим
 134:            acDoc.Editor.SetCurrentView(acView);
 135:        } 
 136:   
 137:        // Сохранить произведённые изменения
 138:        acTrans.Commit();
 139:    }
 140:  }

Примечания переводчика:
1Display Coordinate System (система координат отображения) - координатная система, в которую будут преобразованы данные об объектах прежде, чем те будут отображены.
2 - та точка, на которую мы смотрим, на которой фокусируемся.
3 - т.е. до той точки, из которой мы смотрим на целевую точку.
4 - это угол, полученный от проходящего из целевой точки в точку нахождения камеры вектора, между этим вектором и плоскостью XY.

Comments