简体   繁体   English

用不使用System.Runtime.InteropServices的东西替换[StructLayout]?

[英]Replace [StructLayout] with something that doesn't use System.Runtime.InteropServices?

I have no experience with low level programing and I need this piece of code to not use [StructLayout(LayoutKind.Explicit)]. 我没有底层编程的经验,我需要这段代码不要使用[StructLayout(LayoutKind.Explicit)]。 My site runs on a shared host and in medium trust. 我的网站在共享主机上运行,​​并具有中等信任度。 So it won't run if this code is in there. 因此,如果其中包含此代码,它将不会运行。

Update: I'm using this inside a Octree to Quantize a png file. 更新:我在Octree中使用它来量化png文件。

Does anyone know a work around? 有人知道解决方法吗?

Update New question here => Is there any way to do Image Quantization safely and with no Marshalling? 在这里更新新问题=> 是否可以安全地进行图像量化而无需编组?

/// <summary>
        /// Struct that defines a 32 bpp colour
        /// </summary>
        /// <remarks>
        /// This struct is used to read data from a 32 bits per pixel image
        /// in memory, and is ordered in this manner as this is the way that
        /// the data is layed out in memory
        /// </remarks>
        [StructLayout(LayoutKind.Explicit)]
        public struct Color32
        {

            public Color32(IntPtr pSourcePixel)
            {
                this = (Color32)Marshal.PtrToStructure(pSourcePixel, typeof(Color32));

            }

            /// <summary>
            /// Holds the blue component of the colour
            /// </summary>
            [FieldOffset(0)]
            public byte Blue;
            /// <summary>
            /// Holds the green component of the colour
            /// </summary>
            [FieldOffset(1)]
            public byte Green;
            /// <summary>
            /// Holds the red component of the colour
            /// </summary>
            [FieldOffset(2)]
            public byte Red;
            /// <summary>
            /// Holds the alpha component of the colour
            /// </summary>
            [FieldOffset(3)]
            public byte Alpha;

            /// <summary>
            /// Permits the color32 to be treated as an int32
            /// </summary>
            [FieldOffset(0)]
            public int ARGB;

            /// <summary>
            /// Return the color for this Color32 object
            /// </summary>
            public Color Color
            {
                get { return Color.FromArgb(Alpha, Red, Green, Blue); }
            }
        }

Interoperating with native code and memory is an inherently unsafe operation. 与本机代码和内存进行互操作本质上是不安全的。 Any calls to the Marshal class will fail as well. 对元帅课程的任何致电也会失败。 You can't access the memory, or do any Interop unless you have full trust level. 除非您具有完全的信任级别,否则您将无法访问内存或执行任何Interop。

Marshal.PtrToStructure Method (IntPtr, Type) won't work anyway since it requires Marshal.PtrToStructure方法(IntPtr,类型)无论如何都无法正常工作

 [SecurityPermissionAttribute( SecurityAction.LinkDemand, Flags = SecurityPermissionFlag.UnmanagedCode)] 

You could deal with the offsets yourself safely, but you would have to do it without using Marshal. 您可以自己安全地处理偏移量,但是您必须在不使用元帅的情况下进行处理。
I suggest also moving to using uints for simplicity. 为了简化起见,我建议也使用uints。

public struct Color32
{
    const uint BlueMask  = 0xFF000000;       
    const uint GreenMask = 0x00FF0000;
    const uint RedMask   = 0x0000FF00;
    const uint AlphaMask = 0x000000FF;
    const int BlueShift  = 24;       
    const int GreenShift = 16;
    const int RedShift   = 8;
    const int AlphaShift = 0;

    private byte GetComponent(uint mask, int shift)
    {
        var b = (this.ARGB & mask);
        return (byte) (b >> shift);            
    } 

    private void SetComponent(int shift, byte value)
    {
        var b = ((uint)value) << shift
        this.ARGB |= b;
    } 

    public byte Blue 
    {
        get { return GetComponent(BlueMask, BlueShift); }
        set { SetComponent(BlueShift, value); }
    }

    public byte Green
    {
        get { return GetComponent(GreenMask, GreenShift); }
        set { SetComponent(GreenShift, value); }
    }

    public byte Red
    {
        get { return GetComponent(RedMask, RedShift); }
        set { SetComponent(RedShift, value); }
    }

    public byte Alpha
    {
        get { return GetComponent(AlphaMask, AlphaShift); }
        set { SetComponent(AlphaShift, value); }
    }

    /// <summary>
    /// Permits the color32 to be treated as an UInt32
    /// </summary>
    public uint ARGB;

    /// <summary>
    /// Return the color for this Color32 object
    /// </summary>
    public Color Color
    {
        get { return Color.FromArgb(Alpha, Red, Green, Blue); }
    }
}

however it would appear that what you want to do is convert an int32 in one byte order to the reverse. 但是,您似乎想要做的是将int32以一个字节顺序转换为相反的顺序。
For this you have System.Net.IPAddress.HostToNetworkOrder (nasty usage in this regard, you are simply using it to reverse the endianess rather than being specific about which ordering you intend) 为此,您具有System.Net.IPAddress.HostToNetworkOrder (在这方面令人讨厌的用法,您只是在使用它来反转字节序,而不是明确要预定的顺序)

so if you could read your input data as simple int32 values then do: 因此,如果您可以将输入数据读取为简单的int32值,请执行以下操作:

static Color FromBgra(int bgra)
{
    return Color.FromArgb(System.Net.IPAddress.HostToNetworkOrder(bgra));
}

This would likely be much simpler. 这可能会更简单。

You could just store the int ARGB, and use a BitConverter to convert it to the 4 bytes for your color return. 您可以只存储int ARGB,然后使用BitConverter将其转换为4个字节以返回颜色。

Even better, just store the int, and use Color.FromArgb(Int32) . 更好的是,只需存储int并使用Color.FromArgb(Int32)即可

Both of these approaches eliminate the need to store the individual bytes, so you can completely eliminate the StructLayout attribute. 这两种方法都消除了存储单个字节的需要,因此您可以完全消除StructLayout属性。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 又一个System.Runtime.InteropServices错误 - Yet another System.Runtime.InteropServices error 使用System.Runtime.InteropServices但找不到HandleRef - Using System.Runtime.InteropServices but HandleRef is not found 无法加载文件或程序集&#39;System.Runtime.InteropServices&#39; - Could not load file or assembly 'System.Runtime.InteropServices' 错误CS0234:名称空间“System.Runtime.InteropServices”中不存在类型或命名空间名称“CustomMarshalers” - Error CS0234: The type or namespace name 'CustomMarshalers' does not exist in the namespace 'System.Runtime.InteropServices' 使 Unity 意识到 System.Runtime.InteropServices 以使用 HoloToolKit 为 HoloLens 构建项目 - Make Unity aware of System.Runtime.InteropServices to build project for HoloLens using HoloToolKit 即使在包含System.Runtime.InteropServices的情况下,也无法在文件后面的asp.net代码中定义DllImport - DllImport not defined in asp.net code behind file even when including System.Runtime.InteropServices 使用 Windows 窗体生成 Word 文档不适用于所有 PC:System.Runtime.InteropServices.COMException (0x800A16CA) - Producing Word document with windows form doesn't work for all PCs: System.Runtime.InteropServices.COMException (0x800A16CA) &#39;System.Runtime.InteropServices.COMException&#39; - 'System.Runtime.InteropServices.COMException' System.Runtime.InteropServices.COMException - System.Runtime.InteropServices.COMException &#39;System.Runtime.InteropServices.ExternalException&#39; - 'System.Runtime.InteropServices.ExternalException'
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM