zoukankan      html  css  js  c++  java
  • 自己画WinForm 皮肤包括默认控件

    好久没来博客园,今天捣鼓到现在就是为了把之前的皮肤控件完善好,

    之前也看了很多技术文章,大多数都是自己重写系统控件实现换肤,几乎没有像东日的(IrisSkin)控件一样 添加一个组件 把系统的皮肤全换掉,我曾经也是重写系统的控件,但我就喜欢瞎捣鼓,于是就开始找这方面的资料,苦于没学过底层,对windows窗口 以及消息循环机制不了解,找资料也基本上白搭了许久,但最后以为自己能想到的最笨的方法实现 了继承了自己写的父窗口,那么窗口添加的控件就是自己画的 而不是系统画的,

    先上传一张效果图:

    整天效果应该也还算勉强吧,目前我也就写了这几个控件的美化,虽然这破代码捣鼓好几天了,但代码依旧混乱不堪,加上反编译了微软的部分东西,因为想尽快出来,代码都没看,直接复制过来修改成编译不报错就完事了,

    现在我来说说我实现的思路:

    前题条件继承的是自己写的FormBase
    然后重写了系统的OnControlAdded 方法,在这里为每个控件添加美化的类,

    可怎么添加了? 找了好久,找到了一个可拦截Control消息的接口:IWindowTarget 接口(具体请参考 MSDN 微软不建议直接使用的一个类)

    Control 公开并允许修改这个接口的信息,

    IWindowTarget 接口有两个方法,一个是更换控件句柄的(也许应该叫设置控件句柄) 还有一个就是处理 Windows 消息的OnMessage
     我要做的就是拦截Windows 消息的重画消息,拦截下来 然后自己画,其它的还是丢个控件处理,(后来发现貌似实现IMessageFilter接口也可以实现)

    好了屁话不多说了 上代码 上demo 没写完  希望大神能帮忙完善下就最好了-.-!

    对了 就是问个2B问题,怎么拦截所有的Form创建或者Form创建句柄时?我用IMessageFilter好像拦截不到,

    唉 代码有点乱,各位将就着看吧

    部分代码:

    using DotNet.Windows.Forms.Internal;
    using System;
    using System.Drawing;
    using System.Drawing.Drawing2D;
    using System.Drawing.Imaging;
    using System.Reflection;
    using System.Runtime.InteropServices;
    using System.Windows.Forms;
    
    namespace DotNet.Windows.Forms
    {
        public abstract class WindowTarget<T> : IWindowTarget
            where T : Control
        {
            private static readonly ControlStyles UserControlStyles;
            private static readonly MethodInfo SetStyleMethod;
            private static readonly MethodInfo SetStateMethod;
            private static readonly PropertyInfo CacheTextInternalProperty;
            private static readonly FieldInfo windowField;
    
            static WindowTarget()
            {
                UserControlStyles = ControlStyles.AllPaintingInWmPaint | ControlStyles.OptimizedDoubleBuffer | ControlStyles.ResizeRedraw | ControlStyles.Selectable | ControlStyles.ContainerControl | ControlStyles.UserPaint;
                SetStyleMethod = typeof(Control).GetMethod("SetStyle",BindingFlags.Instance |BindingFlags.NonPublic);
                SetStateMethod = typeof(Control).GetMethod("SetState", BindingFlags.Instance | BindingFlags.NonPublic);
                windowField = typeof(Control).GetField("window", BindingFlags.Instance | BindingFlags.NonPublic);
                CacheTextInternalProperty = typeof(Control).GetProperty("CacheTextInternal", BindingFlags.Instance | BindingFlags.NonPublic);
            }
            private T m_Control;
            private IWindowTarget m_WindowTarget;
            private MouseState m_MouseState = MouseState.Normal;
            protected WindowTarget(T control)
            {
                m_Control = control;
                m_WindowTarget = m_Control.WindowTarget;
                m_Control.MouseUp += (o, e) => { this.MouseState = MouseState.Up; };
                m_Control.MouseEnter += (o, e) => { this.MouseState = MouseState.Move; };
                m_Control.MouseLeave += (o, e) => { this.MouseState = MouseState.Leave; };
                m_Control.MouseDown += (o, e) => { this.MouseState = MouseState.Down; };
            }
            protected virtual void SetStyle(ControlStyles styles, bool value)
            {
                SetStyleMethod.Invoke(Control, new object[] { styles, value });
            }
            private object window
            {
                get
                {
                    return windowField.GetValue(Control);
                }
            }
            private bool CacheTextInternal
            {
                get
                {
                    return (bool)CacheTextInternalProperty.GetValue(Control, null);
                }
                set
                {
                    CacheTextInternalProperty.SetValue(Control, value, null);
                }
            }
            protected virtual void SetState(int flag, bool value)
            {
                SetStyleMethod.Invoke(Control, new object[] { flag, value });
            }
            protected T Control { get { return m_Control; } }
            protected IWindowTarget Target { get { return m_WindowTarget; } }
            protected abstract void OnPaint(DotNet.Windows.Forms.Internal.PaintEventArgs e);
            protected MouseState MouseState
            {
                get
                {
                    return m_MouseState;
                }
                set
                {
                    if (m_MouseState != value)
                    {
                        m_MouseState = value;
                        Control.Invalidate();
                    }
                }
            }
            protected virtual Image GetImage()
            {
                switch (MouseState)
                {
                    case MouseState.Leave:
                    case MouseState.Normal:
                        return GetNormalImage();
                    case MouseState.Up:
                    case MouseState.Move:
                        return GetMoveImage();
                    case MouseState.Down:
                        return GetDownImage();
                    default:
                        return null;
                }
            }
            protected abstract Image GetNormalImage();
            protected abstract Image GetMoveImage();
            protected abstract Image GetDownImage();
            protected void RendererBackground(Graphics g, Rectangle rect, Image backgroundImage, bool method)
            {
                if (!method)
                {
                    g.DrawImage(backgroundImage, new Rectangle(rect.X + 0, rect.Y, 5, rect.Height), 0, 0, 5, backgroundImage.Height, GraphicsUnit.Pixel);
                    g.DrawImage(backgroundImage, new Rectangle(rect.X + 5, rect.Y, rect.Width - 10, rect.Height), 5, 0, backgroundImage.Width - 10, backgroundImage.Height, GraphicsUnit.Pixel);
                    g.DrawImage(backgroundImage, new Rectangle(rect.X + rect.Width - 5, rect.Y, 5, rect.Height), backgroundImage.Width - 5, 0, 5, backgroundImage.Height, GraphicsUnit.Pixel);
                }
                else
                {
                    RendererBackground(g, rect, 5, backgroundImage);
                }
            }
            /// <summary>
            /// 渲染背景图片,使背景图片不失真
            /// </summary>
            /// <param name="g"></param>
            /// <param name="rect"></param>
            /// <param name="cut"></param>
            /// <param name="backgroundImage"></param>
            protected void RendererBackground(Graphics g, Rectangle rect, int cut, Image backgroundImage)
            {
                //左上角
                g.DrawImage(backgroundImage, new Rectangle(rect.X, rect.Y, cut, cut), 0, 0, cut, cut, GraphicsUnit.Pixel);
                //上边
                g.DrawImage(backgroundImage, new Rectangle(rect.X + cut, rect.Y, rect.Width - cut * 2, cut), cut, 0, backgroundImage.Width - cut * 2, cut, GraphicsUnit.Pixel);
                //右上角
                g.DrawImage(backgroundImage, new Rectangle(rect.X + rect.Width - cut, rect.Y, cut, cut), backgroundImage.Width - cut, 0, cut, cut, GraphicsUnit.Pixel);
                //左边
                g.DrawImage(backgroundImage, new Rectangle(rect.X, rect.Y + cut, cut, rect.Height - cut * 2), 0, cut, cut, backgroundImage.Height - cut * 2, GraphicsUnit.Pixel);
                //左下角
                g.DrawImage(backgroundImage, new Rectangle(rect.X, rect.Y + rect.Height - cut, cut, cut), 0, backgroundImage.Height - cut, cut, cut, GraphicsUnit.Pixel);
                //右边
                g.DrawImage(backgroundImage, new Rectangle(rect.X + rect.Width - cut, rect.Y + cut, cut, rect.Height - cut * 2), backgroundImage.Width - cut, cut, cut, backgroundImage.Height - cut * 2, GraphicsUnit.Pixel);
                //右下角
                g.DrawImage(backgroundImage, new Rectangle(rect.X + rect.Width - cut, rect.Y + rect.Height - cut, cut, cut), backgroundImage.Width - cut, backgroundImage.Height - cut, cut, cut, GraphicsUnit.Pixel);
                //下边
                g.DrawImage(backgroundImage, new Rectangle(rect.X + cut, rect.Y + rect.Height - cut, rect.Width - cut * 2, cut), cut, backgroundImage.Height - cut, backgroundImage.Width - cut * 2, cut, GraphicsUnit.Pixel);
                //平铺中间
                g.DrawImage(backgroundImage, new Rectangle(rect.X + cut, rect.Y + cut, rect.Width - cut * 2, rect.Height - cut * 2), cut, cut, backgroundImage.Width - cut * 2, backgroundImage.Height - cut * 2, GraphicsUnit.Pixel);
            }
            #region IWindowTarget 成员
            void IWindowTarget.OnHandleChange(IntPtr newHandle)
            {
                Target.OnHandleChange(newHandle);
            }
            private BufferedGraphicsContext BufferContext
            {
                get
                {
                    return BufferedGraphicsManager.Current;
                }
            }
            internal static IntPtr SetUpPalette(IntPtr dc, bool force, bool realizePalette)
            {
                IntPtr halftonePalette = Graphics.GetHalftonePalette();
                IntPtr ptr2 = SafeNativeMethods.SelectPalette(new HandleRef(null, dc), new HandleRef(null, halftonePalette), force ? 0 : 1);
                if ((ptr2 != IntPtr.Zero) && realizePalette)
                {
                    SafeNativeMethods.RealizePalette(new HandleRef(null, dc));
                }
                return ptr2;
            }
            private void WmPaint(ref  Message m)
            {
                bool flag = true;
                IntPtr zero = IntPtr.Zero;
                NativeMethods.PAINTSTRUCT lpPaint = new NativeMethods.PAINTSTRUCT();
                bool flag2 = false;
                try
                {
                    IntPtr wParam;
                    Rectangle clientRectangle;
                    if (m.WParam == IntPtr.Zero)
                    {
                        zero = Control.Handle;
                        wParam = UnsafeNativeMethods.BeginPaint(new HandleRef(this, zero), ref lpPaint);
                        flag2 = true;
                        clientRectangle = new Rectangle(lpPaint.rcPaint_left, lpPaint.rcPaint_top, lpPaint.rcPaint_right - lpPaint.rcPaint_left, lpPaint.rcPaint_bottom - lpPaint.rcPaint_top);
                    }
                    else
                    {
                        wParam = m.WParam;
                        clientRectangle = Control.ClientRectangle;
                    }
                    if (!flag || ((clientRectangle.Width > 0) && (clientRectangle.Height > 0)))
                    {
                        IntPtr handle = IntPtr.Zero;
                        BufferedGraphics graphics = null;
                        DotNet.Windows.Forms.Internal.PaintEventArgs e = null;
                        System.Drawing.Drawing2D.GraphicsState gstate = null;
                        try
                        {
                            if (flag || (m.WParam == IntPtr.Zero))
                            {
                                handle = SetUpPalette(wParam, false, false);
                            }
                            if (flag)
                            {
                                try
                                {
                                    graphics = this.BufferContext.Allocate(wParam, Control.ClientRectangle);
                                }
                                catch (Exception exception)
                                {
                                    if (ClientUtils.IsCriticalException(exception))
                                    {
                                        throw;
                                    }
                                    flag = false;
                                }
                            }
                            if (graphics != null)
                            {
                                graphics.Graphics.SetClip(clientRectangle);
                                e = new DotNet.Windows.Forms.Internal.PaintEventArgs(graphics.Graphics, clientRectangle);
                                gstate = e.Graphics.Save();
                            }
                            else
                            {
                                e = new DotNet.Windows.Forms.Internal.PaintEventArgs(wParam, clientRectangle);
                            }
                            using (e)
                            {
                                try
                                {
                                    if (((m.WParam == IntPtr.Zero) && true) || flag)
                                    {
                                        this.PaintWithErrorHandling(e, 1);
                                    }
                                }
                                finally
                                {
                                    if (gstate != null)
                                    {
                                        e.Graphics.Restore(gstate);
                                    }
                                    else
                                    {
                                        e.ResetGraphics();
                                    }
                                }
                                this.PaintWithErrorHandling(e, 2);
                                if (graphics != null)
                                {
                                    graphics.Render();
                                }
                            }
                        }
                        finally
                        {
                            if (handle != IntPtr.Zero)
                            {
                                SafeNativeMethods.SelectPalette(new HandleRef(null, wParam), new HandleRef(null, handle), 0);
                            }
                            if (graphics != null)
                            {
                                graphics.Dispose();
                            }
                        }
                    }
                }
                finally
                {
                    if (flag2)
                    {
                        UnsafeNativeMethods.EndPaint(new HandleRef(this, zero), ref lpPaint);
                    }
                }
            }
            protected virtual void OnPaintBackground(DotNet.Windows.Forms.Internal.PaintEventArgs pevent)
            {
                NativeMethods.RECT rect = new NativeMethods.RECT();
                UnsafeNativeMethods.GetClientRect(new HandleRef(this.window, Control.Handle), ref rect);
                this.PaintBackground(pevent, new Rectangle(rect.left, rect.top, rect.right, rect.bottom));
            }
            internal void PaintBackground(DotNet.Windows.Forms.Internal.PaintEventArgs e, Rectangle rectangle)
            {
                this.PaintBackground(e, rectangle, Control.BackColor, Point.Empty);
            }
    
            internal void PaintBackground(DotNet.Windows.Forms.Internal.PaintEventArgs e, Rectangle rectangle, System.Drawing.Color backColor)
            {
                this.PaintBackground(e, rectangle, backColor, Point.Empty);
            }
            private bool RenderColorTransparent(System.Drawing.Color c)
            {
                return ((c.A < 0xff));
            }
            internal void PaintTransparentBackground(DotNet.Windows.Forms.Internal.PaintEventArgs e, Rectangle rectangle)
            {
                this.PaintTransparentBackground(e, rectangle, null);
            }
            internal static bool IsImageTransparent(Image backgroundImage)
            {
                return ((backgroundImage != null) && ((backgroundImage.Flags & 2) > 0));
            }
            internal static Rectangle CalculateBackgroundImageRectangle(Rectangle bounds, Image backgroundImage, ImageLayout imageLayout)
            {
                Rectangle rectangle = bounds;
                if (backgroundImage != null)
                {
                    switch (imageLayout)
                    {
                        case ImageLayout.None:
                            rectangle.Size = backgroundImage.Size;
                            return rectangle;
    
                        case ImageLayout.Tile:
                            return rectangle;
    
                        case ImageLayout.Center:
                            {
                                rectangle.Size = backgroundImage.Size;
                                Size size = bounds.Size;
                                if (size.Width > rectangle.Width)
                                {
                                    rectangle.X = (size.Width - rectangle.Width) / 2;
                                }
                                if (size.Height > rectangle.Height)
                                {
                                    rectangle.Y = (size.Height - rectangle.Height) / 2;
                                }
                                return rectangle;
                            }
                        case ImageLayout.Stretch:
                            rectangle.Size = bounds.Size;
                            return rectangle;
    
                        case ImageLayout.Zoom:
                            {
                                Size size2 = backgroundImage.Size;
                                float num = ((float)bounds.Width) / ((float)size2.Width);
                                float num2 = ((float)bounds.Height) / ((float)size2.Height);
                                if (num >= num2)
                                {
                                    rectangle.Height = bounds.Height;
                                    rectangle.Width = (int)((size2.Width * num2) + 0.5);
                                    if (bounds.X >= 0)
                                    {
                                        rectangle.X = (bounds.Width - rectangle.Width) / 2;
                                    }
                                    return rectangle;
                                }
                                rectangle.Width = bounds.Width;
                                rectangle.Height = (int)((size2.Height * num) + 0.5);
                                if (bounds.Y >= 0)
                                {
                                    rectangle.Y = (bounds.Height - rectangle.Height) / 2;
                                }
                                return rectangle;
                            }
                    }
                }
                return rectangle;
            }
            internal static void DrawBackgroundImage(Graphics g, Image backgroundImage, Color backColor, ImageLayout backgroundImageLayout, Rectangle bounds, Rectangle clipRect, Point scrollOffset, RightToLeft rightToLeft)
            {
                if (g == null)
                {
                    throw new ArgumentNullException("g");
                }
                if (backgroundImageLayout == ImageLayout.Tile)
                {
                    using (TextureBrush brush = new TextureBrush(backgroundImage, WrapMode.Tile))
                    {
                        if (scrollOffset != Point.Empty)
                        {
                            Matrix transform = brush.Transform;
                            transform.Translate((float)scrollOffset.X, (float)scrollOffset.Y);
                            brush.Transform = transform;
                        }
                        g.FillRectangle(brush, clipRect);
                        return;
                    }
                }
                Rectangle rect = CalculateBackgroundImageRectangle(bounds, backgroundImage, backgroundImageLayout);
                if ((rightToLeft == RightToLeft.Yes) && (backgroundImageLayout == ImageLayout.None))
                {
                    rect.X += clipRect.Width - rect.Width;
                }
                using (SolidBrush brush2 = new SolidBrush(backColor))
                {
                    g.FillRectangle(brush2, clipRect);
                }
                if (!clipRect.Contains(rect))
                {
                    if ((backgroundImageLayout == ImageLayout.Stretch) || (backgroundImageLayout == ImageLayout.Zoom))
                    {
                        rect.Intersect(clipRect);
                        g.DrawImage(backgroundImage, rect);
                    }
                    else if (backgroundImageLayout == ImageLayout.None)
                    {
                        rect.Offset(clipRect.Location);
                        Rectangle destRect = rect;
                        destRect.Intersect(clipRect);
                        Rectangle rectangle3 = new Rectangle(Point.Empty, destRect.Size);
                        g.DrawImage(backgroundImage, destRect, rectangle3.X, rectangle3.Y, rectangle3.Width, rectangle3.Height, GraphicsUnit.Pixel);
                    }
                    else
                    {
                        Rectangle rectangle4 = rect;
                        rectangle4.Intersect(clipRect);
                        Rectangle rectangle5 = new Rectangle(new Point(rectangle4.X - rect.X, rectangle4.Y - rect.Y), rectangle4.Size);
                        g.DrawImage(backgroundImage, rectangle4, rectangle5.X, rectangle5.Y, rectangle5.Width, rectangle5.Height, GraphicsUnit.Pixel);
                    }
                }
                else
                {
                    ImageAttributes imageAttr = new ImageAttributes();
                    imageAttr.SetWrapMode(WrapMode.TileFlipXY);
                    g.DrawImage(backgroundImage, rect, 0, 0, backgroundImage.Width, backgroundImage.Height, GraphicsUnit.Pixel, imageAttr);
                    imageAttr.Dispose();
                }
            }
            internal void PaintTransparentBackground(DotNet.Windows.Forms.Internal.PaintEventArgs e, Rectangle rectangle, System.Drawing.Region transparentRegion)
            {
                Graphics g = e.Graphics;
                Control parentInternal = Control.Parent;
                if (parentInternal != null)
                {
                    if (Application.RenderWithVisualStyles) // parentInternal.RenderTransparencyWithVisualStyles)
                    {
                        System.Drawing.Drawing2D.GraphicsState gstate = null;
                        if (transparentRegion != null)
                        {
                            gstate = g.Save();
                        }
                        try
                        {
                            if (transparentRegion != null)
                            {
                                g.Clip = transparentRegion;
                            }
                            ButtonRenderer.DrawParentBackground(g, rectangle, Control);
                            return;
                        }
                        finally
                        {
                            if (gstate != null)
                            {
                                g.Restore(gstate);
                            }
                        }
                    }
                    Rectangle rectangle2 = new Rectangle(-Control.Left, -Control.Top, parentInternal.Width, parentInternal.Height);
                    Rectangle clipRect = new Rectangle(rectangle.Left + Control.Left, rectangle.Top + Control.Top, rectangle.Width, rectangle.Height);
                    using (WindowsGraphics graphics2 = WindowsGraphics.FromGraphics(g))
                    {
                        graphics2.DeviceContext.TranslateTransform(-Control.Left, -Control.Top);
                        using (DotNet.Windows.Forms.Internal.PaintEventArgs args = new DotNet.Windows.Forms.Internal.PaintEventArgs(graphics2.GetHdc(), clipRect))
                        {
                            if (transparentRegion != null)
                            {
                                args.Graphics.Clip = transparentRegion;
                                args.Graphics.TranslateClip(-rectangle2.X, -rectangle2.Y);
                            }
                            try
                            {
                                //this.InvokePaintBackground(parentInternal, args);
                                //this.InvokePaint(parentInternal, args);
                            }
                            finally
                            {
                                if (transparentRegion != null)
                                {
                                    args.Graphics.TranslateClip(rectangle2.X, rectangle2.Y);
                                }
                            }
                        }
                        return;
                    }
                }
                g.FillRectangle(SystemBrushes.Control, rectangle);
            }
            internal void PaintBackground(DotNet.Windows.Forms.Internal.PaintEventArgs e, Rectangle rectangle, System.Drawing.Color backColor, Point scrollOffset)
            {
                backColor = Color.Transparent;
                //ControlStyles.SupportsTransparentBackColor;
                this.PaintTransparentBackground(e, rectangle);
                //if (this.RenderColorTransparent(backColor))
                //{
                //    this.PaintTransparentBackground(e, rectangle);
                //}
                bool flag = ((Control is FormBase) || (this is MdiClient)) && Control.IsMirrored;
                if (((Control.BackgroundImage != null) && !SystemInformation.HighContrast) && !flag)
                {
                    if ((Control.BackgroundImageLayout == ImageLayout.Tile) && IsImageTransparent(Control.BackgroundImage))
                    {
                        PaintTransparentBackground(e, rectangle);
                    }
                    Point autoScrollPosition = scrollOffset;
                    if ((Control is ScrollableControl) && (autoScrollPosition != Point.Empty))
                    {
                        autoScrollPosition = ((ScrollableControl)(Control)Control).AutoScrollPosition;
                    }
                    if (IsImageTransparent(Control.BackgroundImage))
                    {
                        PaintBackColor(e, rectangle, backColor);
                    }
                    DrawBackgroundImage(e.Graphics, Control.BackgroundImage, backColor, Control.BackgroundImageLayout, Control.ClientRectangle, rectangle, autoScrollPosition, Control.RightToLeft);
                }
                else
                {
                    PaintBackColor(e, rectangle, backColor);
                }
            }
            private static void PaintBackColor(DotNet.Windows.Forms.Internal.PaintEventArgs e, Rectangle rectangle, System.Drawing.Color backColor)
            {
                System.Drawing.Color nearestColor = backColor;
                if (nearestColor.A == 0xff)
                {
                    using (WindowsGraphics graphics = ((e.HDC != IntPtr.Zero) && ((short)Screen.PrimaryScreen.BitsPerPixel > 8)) ? WindowsGraphics.FromHdc(e.HDC) : WindowsGraphics.FromGraphics(e.Graphics))
                    {
                        nearestColor = graphics.GetNearestColor(nearestColor);
                        using (WindowsBrush brush = new WindowsSolidBrush(graphics.DeviceContext, nearestColor))
                        {
                            graphics.FillRectangle(brush, rectangle);
                        }
                        return;
                    }
                }
                if (nearestColor.A > 0)
                {
                    using (Brush brush2 = new SolidBrush(nearestColor))
                    {
                        e.Graphics.FillRectangle(brush2, rectangle);
                    }
                }
            }
            private void PaintWithErrorHandling(DotNet.Windows.Forms.Internal.PaintEventArgs e, short layer)
            {
                try
                {
                    this.CacheTextInternal = true;
                    bool flag = true;
                    try
                    {
                        switch (layer)
                        {
                            case 1:
                                this.OnPaintBackground(e);
                                break;
                            case 2:
                                this.OnPaint(e);
                                break;
                        }
                        flag = false;
                    }
                    finally
                    {
                        if (flag)
                        {
                            this.SetState(0x400000, true);
                            Control.Invalidate();
                        }
                    }
                }
                finally
                {
                    this.CacheTextInternal = false;
                }
            }
            void IWindowTarget.OnMessage(ref Message m)
            {
                if (m.Msg == 15)
                {
                    WmPaint(ref m);
                    return;
                }
                Target.OnMessage(ref m);
            }
    
            #endregion
        }
    }
    View Code

    http://files.cnblogs.com/dotnet-org-cn/DotNet.Framework.rar

    最后打个小广告:中国.NET协会(http://www.dotnet.org.cn
    腾讯企鹅群:45132984中国.NET协会
    博客园地址:http://http://www.cnblogs.com/dotnet-org-cn
         国内唯一一个以非盈利的.NET协会,致力打造国内具有权威性、价值性的.NET协会。

  • 相关阅读:
    Android开发之Sqlite的使用
    ZOJ 3607 Lazier Salesgirl
    ZOJ 3769 Diablo III
    ZOJ 2856 Happy Life
    Ural 1119 Metro
    Ural 1146 Maximum Sum
    HDU 1003 Max Sum
    HDU 1160 FatMouse's Speed
    Ural 1073 Square Country
    Ural 1260 Nudnik Photographer
  • 原文地址:https://www.cnblogs.com/dotnet-org-cn/p/4166250.html
Copyright © 2011-2022 走看看