Date: 29.01.2017 7:03:28
Используя класс Clipboard:
IDataObject myDataObject=Clipboard.GetDataObject();
String[] allFormats = myDataObject.GetFormats();
foreach(string s in allFormats)
{
if(s==DataFormats.UnicodeText)
{
string text=myDataObject.GetData(DataFormats.UnicodeText);
MessageBox.Show("UnicodeText size: "+ ((text.Length+1) * 2).ToString());
}
else
{
object val=myDataObject.GetData(s);
int size=System.Runtime.InteropServices.Marshal.SizeOf(val);
MessageBox.Show(s+" size: " + (size).ToString());
}
}
С размером не все так просто, он зависит от типа данных... Зная тип и формулу, можно размер посчитать (в примере размер Юникод-строки). Для произвольного объекта можно взять размер неуправляемой памяти (Marshal.SizeOf), но не факт что это сработает.
Добавлено: да, Marshal.SizeOf бесполезен в этом случае. См. ниже рабочий метод.
Date: 29.01.2017 11:18:44
Вот нашел еще один способ получения размера произвольного формата в буфере обмена (работает в 80% случаев). Возвращает размер выделенной памяти, который больше или равен размеру самих данных, но для некоторых форматов возвращается слишком маленькое значение или 0:
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using System.Runtime.InteropServices;
namespace Test
{
public partial class Form1 : Form
{
[DllImport("user32.dll", SetLastError = true)]
static extern bool OpenClipboard(IntPtr hWndNewOwner);
[DllImport("user32.dll")]
static extern IntPtr GetClipboardData(uint uFormat);
[DllImport("kernel32.dll")]
static extern UIntPtr GlobalSize(IntPtr hMem);
[DllImport("user32.dll", SetLastError = true)]
static extern bool CloseClipboard();
public uint GetClipboardDataSize(string fmt)//получение размера блока памяти в буфере обмена
{
DataFormats.Format myFormat;
int id;
IntPtr hMem;
uint size;
OpenClipboard(IntPtr.Zero);
myFormat = DataFormats.GetFormat(fmt);
id = myFormat.Id;
hMem = GetClipboardData((uint)id);
size = (uint)GlobalSize(hMem);
CloseClipboard();
return size;
}
public Form1()
{
InitializeComponent();
}
private void button1_Click(object sender, EventArgs e)
{
IDataObject myDataObject = Clipboard.GetDataObject();
String[] allFormats = myDataObject.GetFormats();//получение списка форматов
StringBuilder sb=new StringBuilder(300);
foreach (string s in allFormats)
{
sb.AppendLine(s + ": " + GetClipboardDataSize(s) + " bytes");
}
MessageBox.Show(sb.ToString());
}
}
}
Тестирование показало, что Marshal.SizeOf не работает (в смысле, для объектов буфера обмена), а также что формула размера для Юникод-текста все-таки
((text.Length+1)
* 2) а не
((text.Length+2)
* 2)Автор: VadimTagil