Доброго времени суток! Народ нужна ваша профессиональная помощь!! Мне как инженеру конструктору, в архиве несколько 1000 документов, необходимо автоматизировать работу с конструкторской документацией.
Для этого на Visual C# сделал оболочку, в базах sql регистрирую чертежи.
Перед регистрацией в базе чертежа или спецификации, его открываю считываю содержимое штампа.
int[] myArr = new int[10]; // Коды строк чертежа
myArr[0] = 2; // Обозначение
myArr[1] = 1; // Наименование
myArr[2] = 5; // Масса
myArr[3] = 3; // Материал
myArr[4] = 110; // Разработал
myArr[5] = 111; // Проверил
myArr[6] = 113; // нач КБ
myArr[7] = 114; // Н контроль
myArr[8] = 115; // Утв
myArr[9] = 25; // Первичное прим.
ksDocument2D Doc = (ksDocument2D)kompas.Document2D();
Doc.ksOpenDocument((treeView1.SelectedNode.FullPath + @"\" + checkedListBox1.Text), true);
ksDocumentParam DocPm = (ksDocumentParam)kompas.GetParamStruct(35);
ksStamp st = (ksStamp)Doc.GetStamp();
st.ksOpenStamp();
foreach (int n in myArr)
{
st.ksColumnNumber(n);
ksTextItemParam itemParam = (ksTextItemParam)kompas.GetParamStruct((short)StructType2DEnum.ko_TextItemParam);
ksTextLineParam TextLine = (ksTextLineParam)kompas.GetParamStruct((short)StructType2DEnum.ko_TextLineParam);
ksDynamicArray f = (ksDynamicArray)st.ksGetStampColumnText(n);
if (f != null)
{
string str_stamp = "";
int rr = f.ksGetArrayCount();// определяет количество строк
for (int i1 = 0; i1 < f.ksGetArrayCount(); i1++ )
{
f.ksGetArrayItem(i1, TextLine); // читает определенную строку строку
ksDynamicArray f1 = (ksDynamicArray)TextLine.GetTextItemArr();
f1.ksGetArrayItem(0, itemParam);
str_stamp = str_stamp + itemParam.s;
}
ls.Add(str_stamp);
}
else
{
ls.Add("");
}
Получаю всю интересующую меня информацию. Но не могу прочитать, материал когда материал в 3 графе записан в виде дроби!!!! См. приложение.
Далее при необходимости из базы вызываю чертеж или спецификацию и заполняю штамп. Следующим образом.
ksDocument2D doc = (ksDocument2D)kompas.Document2D();
doc.ksOpenDocument((Directory + @"\" + Stamp[1].ToString().Trim() + ".cdw"), false);
ksStamp S = (ksStamp)doc.GetStamp(); // переменная штамп
S.ksOpenStamp();
ksTextItemParam itemParam = (ksTextItemParam)kompas.GetParamStruct((short)StructType2DEnum.ko_TextItemParam);
ksTextItemFont itemFont = (ksTextItemFont)itemParam.GetItemFont();
itemFont.SetBitVectorValue(ldefin2d.NEW_LINE, true);
S.ksColumnNumber(2);
itemParam.s = Stamp[2].ToString();//"Обозначение";
S.ksTextLine(itemParam);
S.ksColumnNumber(1);
itemParam.s = Stamp[3].ToString();// "Наименование";
doc.ksTextLine(itemParam);
S.ksColumnNumber(25);
itemParam.s = Stamp[4].ToString();// "Первичное прим";
doc.ksTextLine(itemParam);
S.ksColumnNumber(10);
itemParam.s = "Нач КБ";
S.ksSetTextLineAlign(0);
S.ksTextLine(itemParam);
S.ksColumnNumber(110);
itemParam.s = Stamp[5].ToString(); ; //---- разработал
S.ksTextLine(itemParam);
S.ksColumnNumber(111);
itemParam.s = rd["Cheked"].ToString(); //---- Проверил
S.ksTextLine(itemParam);
S.ksColumnNumber(112);
itemParam.s = rd["TechControl"].ToString(); //---- Т. контрол
S.ksTextLine(itemParam);
S.ksColumnNumber(113);
itemParam.s = rd["HeadKB"].ToString(); //---- Нач КБ
S.ksTextLine(itemParam);
S.ksColumnNumber(114);
itemParam.s = rd["StandartContrl"].ToString(); //---- Н. контрл
S.ksTextLine(itemParam);
S.ksColumnNumber(115);
itemParam.s = rd["Approved"].ToString(); //---- Утвердил
S.ksTextLine(itemParam);
S.ksCloseStamp();
Все заполняется вроде бы проблем нет, но не могу внести материал в виде дроби.
А также когда чертеж сборочный то не могу записать в графе 1 под наименованием "Сборочный чертеж". Пишется только в одну строку. Хотя при внесении чертежа в базу я читаю и 1-ую и 2-ую чтроку.
И так на повестке 3 вопроса:
1- как прочитать и идентифицировать материал который записан в виде дроби ?
2 - как внести материал в виде дроби в штамп чертежа?
3 - как в наименовании чертежа разместить 2 надписи одна под другой?
S.ksOpenStamp();
ksDynamicArray DynamicArray = (ksDynamicArray)kompas.GetDynamicArray((short)StructType2DEnum.ko_TextLineParam);
S.ksSetStampColumnText(1, DynamicArray); - в SDK есть такая вот функция, но сколько я с ней не бился она пока показывает 0. Возможно не верно указываю параметры
Дробь можно прочитать и записать одной строкой с использованием управляющих символов.
http://forum.ascon.ru/index.php/topic,23519.msg165572.html#msg165572
S:='Лист$dБ-60х3000х7000 ГОСТ 19903-74;12Х2НМФА-2-а ГОСТ 11269-76$';
Работу с текстом можете посмотреть в примерах: Step3, Step3a и Step5.
Две надписи одна над другой.
http://forum.ascon.ru/index.php/topic,903.msg4521.html#msg4521
Большое спасибо! все работает! :)
Доброго времени суток! Народ вновь нужна ваша профессиональная помощь!!
Продолжаю работать над своей программой, столкнулся вот с такой интересной проблемой.
С помощью KGAX просматриваю чертежи которые находятся у меня в базе. Для этого, для каждого чертежа создаю ,новую форму с axKGAX. И там открываю. см. код ниже. Вроде все работает. НО!!! Когда параллельно с программой включен Компас, начинаются проблемы, а именно - пропадают функция закладок в Окно-> Показать закладки. А так же чертежи могут открыться не в просмотровом окне а в компасе. И так же при просмотре окон ( Окно-> Все окна ) тоже в компасе можно открыть просматриваемый документ.
А этого ни как нельзя допустить, потому что часть документов может находиться в утвержденном архиве и все изменения должны быть только через извещение.
1. Отсюда вопрос!!!! Как можно AxKGAX присвоить новый процесс kompas.exe, что бы AxKGAX не цеплялся к уже открытому компасу, а работал в своем! А после закрытия все окон я бы его закрывал!
2. А так же хочу узнать у меня не работает MoveViewDocument(); для того что бы перемещать документ, как правильно его объявить??
Например ZoomEntireDocument() прекрасно отрабатывает при двойном нажатии мышки!
Жду ваших предложений!!
public List<Form> _MasiveForm = new List<Form>();
public List<string> _MasiveAxKGAX = new List<string>();
public Form[] ViewForm = new Form[10];
AxKGAXLib.AxKGAX[] axKGAX1 = new AxKGAXLib.AxKGAX[10];
public int i = 0;
public void CreateViewForm(int i,string NameForm, string TextForm, string NameFile, string extension)
{
if (!File.Exists(Set.Dir + @"\" + NameFile.Trim() + extension))
{
MessageBox.Show("Документ " + TextForm + " не обнаружен в архиве КД. Проверьте в Параметрах указанный путь к архиву");
return;
}
i = _MasiveForm.Count;
ViewForm = new Form();
axKGAX1 = new AxKGAXLib.AxKGAX();
//------------------------------------------------
//KompasObject k = axKGAX1.GetKompasObject();
ViewForm.AutoScaleDimensions = new System.Drawing.SizeF(6F, 13F);
ViewForm.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
ViewForm.Name = NameForm;
ViewForm.Text = TextForm;
ViewForm.Height = (System.Windows.Forms.Screen.GetWorkingArea(this).Height); // высота формы во весь экран
ViewForm.StartPosition = FormStartPosition.CenterScreen; //Центровка по экрану
ViewForm.Width = (System.Windows.Forms.Screen.GetWorkingArea(this).Width) / 2; // ширина формы
ViewForm.FormClosed += new System.Windows.Forms.FormClosedEventHandler(ViewForm_FormClosed);
ViewForm.ResumeLayout(false);
ViewForm.Enabled = true;
ViewForm.Visible = true;
ViewForm.Show();
System.ComponentModel.ComponentResourceManager resources = new System.ComponentModel.ComponentResourceManager(typeof(MainForm1));
((System.ComponentModel.ISupportInitialize)(axKGAX1)).BeginInit();
ViewForm.SuspendLayout();
axKGAX1.Dock = System.Windows.Forms.DockStyle.Top;
axKGAX1.Size = new System.Drawing.Size(ViewForm.Height - 100, ViewForm.Width);
//--------------------------------------------------------------------------------------------------
axKGAX1.Anchor = ((System.Windows.Forms.AnchorStyles)((((System.Windows.Forms.AnchorStyles.Top
| System.Windows.Forms.AnchorStyles.Bottom)
| System.Windows.Forms.AnchorStyles.Left)
| System.Windows.Forms.AnchorStyles.Right))); // Описание формы axKGAX на новой создаваемой панели
//---------------------------------------------------------------------------------------------------
axKGAX1.Enabled = true;
axKGAX1.Location = new System.Drawing.Point(0, 0);
axKGAX1.Name = "axKGAX1" + Convert.ToString(i);
axKGAX1.OcxState = ((System.Windows.Forms.AxHost.State)(resources.GetObject("axKGAX1.OcxState")));
axKGAX1.TabIndex = 0;
ViewForm.Controls.Add(axKGAX1);
axKGAX1.DocumenFileName = Set.Dir + @"\" + NameFile .Trim() + extension;
//axKGAX1.MoveViewDocument();
axKGAX1.OnKgMouseDblClick += new AxKGAXLib._DKGAXEvents_OnKgMouseDblClickEventHandler(axKGAX1_OnKgMouseDblClick);
((System.ComponentModel.ISupportInitialize)(axKGAX1)).EndInit();
_MasiveForm.Add(ViewForm);
_MasiveAxKGAX.Add(axKGAX1.Name.ToString());
Data_str.Value.Clear();
i++;
}
private void axKGAX1_OnKgMouseDblClick(object sender, AxKGAXLib._DKGAXEvents_OnKgMouseDblClickEvent e)
{
AxKGAXLib.AxKGAX ax = sender as AxKGAXLib.AxKGAX;
for (int i = 0; i < _MasiveAxKGAX.Count; i++)
{
if (_MasiveAxKGAX.ToString() == ax.Name.ToString())
{
axKGAX1.ZoomEntireDocument();
return;
}
}
}
ЦитироватьДля этого, для каждого чертежа создаю ,новую форму с axKGAX. И там открываю
Может для просмотра документа достаточно его отрисовать через KompasObject::ksDrawKompasDocument на простой панельке?
Да наверно вы правы,я тоже уже об этом думал!
Порывшись здесь, на форуме, давно уже нашел пример отрисовки фрагмента компаса на панельке, ее выложил участник - Sabahs.
Но я ни как ее не могу реализовать у себя на c#. Подскажите что делаю не так???
Мои действия:
Создаю простую форму на нее кидаю Panel1.
При загрузки формы открываю компас!
Создаю поле его Handle передаю функции ksDrawKompasDocument,
ksDrawKompasDocument отдает 1 - значит отработало удачно.
Но изображение на панели не отображается.
[System.Runtime.InteropServices.DllImport("user32.dll")]
private static extern IntPtr SetParent(IntPtr hWndChild, // handle to window
IntPtr hWndNewParent // new parent window);
KompasObject kompas;
[System.Runtime.InteropServices.DllImport("user32.dll")]
static extern bool ShowWindow(int hWnd, int nCmdShow);
Panel Pole;
private void Form1_Load(object sender, EventArgs e)
{
Pole = new Panel();
Pole.Visible = true;
SetParent(Pole.Handle, panel1.Handle);
//Pole.Parent = panel1;
Type t = Type.GetTypeFromProgID("KOMPAS.Application.5");
kompas = (KompasObject)Activator.CreateInstance(t);
//kompas.Visible = false;
ShowWindow(kompas.ksGetHWindow(), 0);
kompas.ksDrawKompasDocument((int)Pole.Handle, "d:\\Фрагмент.frw");
}
Потому, что у меня прорисовка реализована в событии WM_PAINT панели.
PS. Хорошая штука отладчик, один рас увидел и все вопросы отпали.
Точно! А я и не подумал! Большое спасибо!
Поместил ksDrawKompasDocument в panel_Paint и сразу показывает!
private void panel_Paint(object sender, PaintEventArgs e)
{
kompas.ksDrawKompasDocument((int)Pole.Handle, "d:\\101-10.06.01.00.01.cdw");
}
Но тут возникает другой вопрос, а можно ли отрисованый чертеж на панели приближать и отдалять как это дает kgax??
А это очень необходимо при просмотре чертежа, особенно больших форматов!
Можно, kgax.DrawToDC - отрисовать документ на заданном HDC.
Добрый день!
Очень понравилась функция ksDrawKompasDocument, на Panel все вырисовываться! для того что бы увеличить документ, воспользовался обычным масштабированием Panel. Увеличивает без снижения качества документа.
Но тут опять столкнулся с проблемкой. На Panel при вызове функции ksDrawKompasDocument, вырисовываться только 1 лист документа, а последующие скрыты.
Сколько листов в документе я могу узнать int i = doc.ksGetDocumentPagesCount();
А как можно указать что бы ksDrawKompasDocument отрисовывал лист 2, лист 3 и т.д. даже допускается выводить их по отдельности.
Конечно данную проблему можно решить и другим способом, например перевести документ в картинку
doc.SaveAsToRasterFormat("D:\\ДСК200-01.02.00.000 Модуль дробления.jpg", Param); и просматривать все его листы. Но хотелось бы обойтись без этого.
Использовать функцию в сообщении выше, не пробовали?
По идеи расширенный аналог функции ksDrawKompasDocument.
Пробовал! Но ни чего не получилось! Поэтому и вернулся к ksDrawKompasDocument.
Что сделал!
Добавил на форму KGAX, при загрузке формы указал файл axKGAX1.DocumenFileName = "d:\\KD000234.spw";
И прошу его отрисовать
bool r = axKGAX1.DrawToDC((int)Pole.Handle, 0, 0, 100, 100); - все время выдает false!
Согласно справки
(int)Pole.Handle - указатель окна где отрисовать.
0, 0, 100, 100 - координаты окна первые 2 цифр, высота и ширина - 2цифры
Подскажите, пожалуйста что не так у меня?
Координаты в функции это прямоугольник в координатах прорисовываемого документа, а Pole.Handle возможно нужно будет заменить на GetDC(Pole.Handle).
Добрый день. функция DrawToDC, начала частично работать! но какие бы координаты прямоугольника не задавал выдает только один кусок чертежа см. фото
[System.Runtime.InteropServices.DllImport("user32.dll")]
static extern IntPtr GetDC(IntPtr hWnd);
bool _ok = false;
private void Form1_Load(object sender, EventArgs e)
{
axKGAX1.DocumenFileName = "D:\\KD000283.cdw";
}
private void button1_Click(object sender, EventArgs e)
{
_ok = true;
panel1.Refresh();
}
private void panel1_Paint(object sender, PaintEventArgs e)
{
if (_ok == true)
{
IntPtr Pole = GetDC(panel1.Handle);
axKGAX1.ZoomEntireDocument();
axKGAX1.DrawToDC((int)Pole, 0, 0, 1500, 1500); // странно прорисовка в панель идет но она все равно выдает false
}
}
Если DrawToDC расширенный аналог функции ksDrawKompasDocument, то как им управлять? Всего то надо приблизить, отдалить, показать документ со всеми листами.
Самое плохое что мне приходиться загружать на форму axKGAX1, а с ним Компас ведет себя неадекватно.
Если так axKGAX1.DrawToDC((int)Pole, 1500, 1500, 3000, 3000); тоже этот же кусок рисует.
Если задать axKGAX1.DrawToDC((int)Pole, 1500, 1500, 3000, 3000);
То изображения нет т.к. оно за полем формы
первые 2 цифры задают координаты точки вставки посмотрите фото я задал там axKGAX1.DrawToDC((int)Pole, 50, 50, 3000, 3000);
смещение от верхнего левого угла поля панели на 50 мм !!
При заданном 3000, 3000 квадрате участок который был ранее только увеличился.
Да axKGAX1.DrawToDC работает не так, как написано в справке, да компонент TKGAX работает ниже плинтуса.
Много листовой документ можно вывести, но с потерей оформления листов, что то там намутили.
PS. TKGAX - не использовался, открыть для просмотра можно только фрагмент или чертёж, для этого нужно сделать двойной щелчок мышью по форме.
Да!! без рамки так не пойдет, он еще и т.т. скрывает!
Спасибо!
Вернусь к старому варианту - одиночные документы буду через ksDrawKompasDocument (жаль что он не может отдельно показать 2 лист)
А все остальные преобразовывать в картинки и показывать отдельно!
Просто для интереса: а почему имено в картинки, а не в PDF (через конвертер КОМПАС) или в xps (через специальную печать на XPS Writer) ? Прим. - Печать нужна именно специальная, чтобы закатать листы с разным форматом в 1 xps файл.
Bordes да я именно так и сделал!
Весь просмотр организован через ПДФ, с ним все гораздо проще, чем с картинками, сразу не догадался!
Доброго времени суток! Народ вновь нужна ваша профессиональная помощь!!
При работе с документацией с помощью своей программой, столкнулся вот с такой интересной проблемой.
Мы делаем конструкторскую документацию для различных фирм, не только для нашей и нас за частую просят в графе штампа "Наименование предприятия" установить тот или иной логотип предприятия.
При редактировании штампа картинку нельзя вставить, но ее можно вставить при редактировании главной таблицы основной надписи. Сервис-> Библиотеки стилей, типов и основных надписей . В приложении см. рис.
При работе с чертежом, эту проблему могу программно обойти - создаю новый слой вставляю картинку, ту которую надо!
А в спецификации такого не могу сделать! Вопрос, можно ли как то программно попасть в главную таблицу штампа и вставить нужный раст. (см. рис. 7)? Или может есть другой способ ?
Как вариант спецификацию делать в формате cdw.
Vin. Увы но так нельзя! потому что поле того как проект окончен я программно из всех спецификаций считаю кол-во деталей, создаю ведомость покупных изделий. а переведя спецификацию в cdw. это все осложнит. Кроме того конструкторам удобнее использовать спецификацию spw,
Хм... как так? :shu: :-)))
Все в рамках ТЗ.
Алхимик! я не понял ваш ответ! Поясните пожалуйста!
Повторюсь - рукам вставить картинку в штамп спецификации я могу (то что вы показываете )
Но как сделать это программно ?
Вот например я заполняю штамп при открытии спецификации из базы чертежей
(В базе уже указано - Наименование, обозначение ..... Принадлежность к предприятию)
ksSpcDocument docSP = (ksSpcDocument)kompas.SpcDocument();
docSP.ksOpenDocument((Directory + @"\" + "`" + Stamp[1].ToString().Trim() + ".spw"), 0);
ksStamp S = (ksStamp)docSP.GetStamp(); // переменная штамп
S.ksOpenStamp();
ksTextItemParam itemParam = (ksTextItemParam)kompas.GetParamStruct((short)StructType2DEnum.ko_TextItemParam);
ksTextItemFont itemFont = (ksTextItemFont)itemParam.GetItemFont();
itemFont.SetBitVectorValue(ldefin2d.NEW_LINE, true);
S.ksColumnNumber(1);
itemParam.s = Stamp[3].ToString();// "Наименование";
S.ksTextLine(itemParam); и т.д. согласно данных базы!!
А здесь мне надо как то описать что бы в зависимости от принадлежности предприятия мне в спецификацию штампа добавлялся Растр.
И вот как это сделать за, что увязаться я не знаю!!
Решал такую задачу. Действительно, только через стиль можно вставить растр. в штамп спецификации. Но на др. компе штамп не откроется с растром. Программно добавить растр в штамп нельзя! Делал следующим образом: Транслировал спецификацию в чертеж, потом создавал слои с растром, потом уже все это хозяйство транслировал в PDF!
Дмитрий спасибо! Понял!
Как вариант вместо логотипа текстом вбивать наименование предприятия!
здравствуйте , так и не разобрался как прочитать и записать к себе в переменную материал если он в виде дроби , прощу продемонстрировать на C#
Все разобрался , если кому нужно , может конечно код кривой но работает :)
ksDocumentParam DocPm = (ksDocumentParam)kompas.GetParamStruct(35);
ksStamp st = (ksStamp)doc2D.GetStamp();
st.ksOpenStamp();
ksTextItemParam item = null;
st.ksColumnNumber(3);
ksDynamicArray arr = (ksDynamicArray)st.ksGetStampColumnText(3);
ksTextItemParam itemParam = (ksTextItemParam)kompas.GetParamStruct((short)StructType2DEnum.ko_TextItemParam);
ksDynamicArray arrpLineText = (ksDynamicArray)kompas.GetDynamicArray(ldefin2d.TEXT_LINE_ARR);
ksTextLineParam itemLineText = (ksTextLineParam)kompas.GetParamStruct((short)StructType2DEnum.ko_TextLineParam);
if (itemLineText == null)
return;
itemLineText.Init();
for (int i = 0, count = arr.ksGetArrayCount(); i < count; i++)
{
arr.ksGetArrayItem(i, itemLineText);
ksDynamicArray arrpTextItem = (ksDynamicArray)itemLineText.GetTextItemArr();
item = (ksTextItemParam)kompas.GetParamStruct((short)StructType2DEnum.ko_TextItemParam);
if (item == null || arrpTextItem == null)
return;
item.Init();
string[] list = new string[arrpTextItem.ksGetArrayCount()];
for (int j = 0, count2 = arrpTextItem.ksGetArrayCount(); j < count2; j++)
{
arrpTextItem.ksGetArrayItem(j, item);
ksTextItemFont textItemFont = (ksTextItemFont)item.GetItemFont();
list[j] = item.s;
}
richTextBox1.Text = list[0] + "d$" + list[1] + ";" + list[2] + "$";
arrpTextItem.ksDeleteArray(); //очистим массив компонент
}
arrpLineText.ksDeleteArray();
arr.ksDeleteArray();
arr = (ksDynamicArray)st.ksGetStampColumnText(3);