Пример #1
0
        private static IIOContainer CreateConfig(IIOFactory factory, IOBuildContext <ConfigAttribute> context)
        {
            var container  = factory.CreateIOContainer(context.ReplaceIOType(typeof(IEnumConfig)));
            var streamType = typeof(EnumConfigStream <>).MakeGenericType(context.DataType);
            var stream     = Activator.CreateInstance(streamType, container.RawIOObject) as IIOStream;

            return(IOContainer.Create(context, stream, container, null, s => s.Flush(), s => s.Sync()));
        }
Пример #2
0
        private static IIOContainer CreateOutput(IIOFactory factory, IOBuildContext <OutputAttribute> context)
        {
            var container  = factory.CreateIOContainer(context.ReplaceIOType(typeof(IEnumOut)));
            var streamType = typeof(EnumOutStream <>).MakeGenericType(context.DataType);
            var stream     = Activator.CreateInstance(streamType, container.RawIOObject) as IOutStream;

            if (context.IOAttribute.AutoFlush)
            {
                return(IOContainer.Create(context, stream, container, null, s => s.Flush()));
            }
            else
            {
                return(IOContainer.Create(context, stream, container));
            }
        }
Пример #3
0
        private static IIOContainer CreateInput(IIOFactory factory, IOBuildContext <InputAttribute> context)
        {
            var container  = factory.CreateIOContainer(context.ReplaceIOType(typeof(IEnumIn)));
            var streamType = typeof(EnumInStream <>).MakeGenericType(context.DataType);
            var stream     = Activator.CreateInstance(streamType, container.RawIOObject) as IInStream;

            // Using ManagedIOStream -> needs to be synced on managed side.
            if (context.IOAttribute.AutoValidate)
            {
                return(IOContainer.Create(context, stream, container, s => s.Sync()));
            }
            else
            {
                return(IOContainer.Create(context, stream, container));
            }
        }
Пример #4
0
        public PointerRegistry()
        {
            RegisterInput <FastValueInput>(
                (factory, context) =>
            {
                var t         = context.IOType;
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(IValueFastIn)));
                var stream    = Activator.CreateInstance(t, container.RawIOObject) as IInStream;

                if (context.IOAttribute.AutoValidate)
                {
                    return(IOContainer.Create(context, stream, container, s => s.Sync()));
                }
                else
                {
                    return(IOContainer.Create(context, stream, container));
                }
            });
            RegisterInput <ValueInput>(
                (factory, context) =>
            {
                var t         = context.IOType;
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(IValueFastIn)));
                var stream    = Activator.CreateInstance(t, container.RawIOObject) as IInStream;

                if (context.IOAttribute.AutoValidate)
                {
                    return(IOContainer.Create(context, stream, container, s => s.Sync()));
                }
                else
                {
                    return(IOContainer.Create(context, stream, container));
                }
            });

            RegisterOutput <ValueOutput>(
                (factory, context) =>
            {
                var t         = context.IOType;
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(IValueOut)));
                var stream    = Activator.CreateInstance(t, container.RawIOObject) as IOutStream;

                return(IOContainer.Create(context, stream, container));
            });
        }
Пример #5
0
        public PinRegistry()
        {
            RegisterInput(typeof(Pin <>), (factory, context) => {
                var attribute = context.IOAttribute;
                var container = factory.CreateIOContainer(typeof(IInStream <>).MakeGenericType(context.DataType), attribute, false);
                var pinType   = typeof(InputPin <>).MakeGenericType(context.DataType);
                var spread    = Activator.CreateInstance(pinType, factory, container.GetPluginIO(), container.RawIOObject) as ISpread;
                if (attribute.AutoValidate)
                {
                    return(IOContainer.Create(context, spread, container, p => p.Sync()));
                }
                else
                {
                    return(IOContainer.Create(context, spread, container));
                }
            },
                          false);

            RegisterOutput(typeof(Pin <>), (factory, context) => {
                var attribute = context.IOAttribute;
                var container = factory.CreateIOContainer(typeof(IOutStream <>).MakeGenericType(context.DataType), attribute, false);
                var pinType   = typeof(OutputPin <>).MakeGenericType(context.DataType);
                var pin       = Activator.CreateInstance(pinType, factory, container.GetPluginIO(), container.RawIOObject) as ISpread;
                return(IOContainer.Create(context, pin, container, null, p => p.Flush()));
            },
                           false);

            RegisterConfig(typeof(Pin <>), (factory, context) => {
                var attribute = context.IOAttribute;
                var container = factory.CreateIOContainer(typeof(IIOStream <>).MakeGenericType(context.DataType), attribute, false);
                var pinType   = typeof(ConfigPin <>).MakeGenericType(context.DataType);
                var spread    = (ISpread)Activator.CreateInstance(pinType, factory, container.GetPluginIO(), container.RawIOObject);
                return(IOContainer.Create(context, spread, container, null, s => s.Flush(), p => p.Sync()));
            },
                           false);
        }
Пример #6
0
        public SpreadRegistry()
        {
            RegisterInput(typeof(ISpread <>), (factory, context) => {
                var attribute  = context.IOAttribute;
                var t          = context.DataType;
                ISpread spread = null;
                if (t.IsGenericType && t.GetGenericArguments().Length == 1)
                {
                    if (typeof(ISpread <>).MakeGenericType(t.GetGenericArguments().First()).IsAssignableFrom(t))
                    {
                        var spreadType = typeof(InputBinSpread <>).MakeGenericType(t.GetGenericArguments().First());

                        if (attribute.IsPinGroup)
                        {
                            spreadType = typeof(InputSpreadList <>).MakeGenericType(t.GetGenericArguments().First());
                        }

                        if (context.BinSizeIOContainer != null)
                        {
                            spread = Activator.CreateInstance(spreadType, factory, attribute.Clone(), context.BinSizeIOContainer) as ISpread;
                        }
                        else
                        {
                            spread = Activator.CreateInstance(spreadType, factory, attribute.Clone()) as ISpread;
                        }
                        if (attribute.AutoValidate)
                        {
                            return(GenericIOContainer.Create(context, factory, spread, s => s.Sync()));
                        }
                        else
                        {
                            return(GenericIOContainer.Create(context, factory, spread));
                        }
                    }
                }
                var container = factory.CreateIOContainer(typeof(IInStream <>).MakeGenericType(context.DataType), attribute, false);
                var pinType   = typeof(InputPin <>).MakeGenericType(context.DataType);
                spread        = Activator.CreateInstance(pinType, factory, container.GetPluginIO(), container.RawIOObject) as ISpread;
                if (attribute.AutoValidate)
                {
                    return(IOContainer.Create(context, spread, container, p => p.Sync()));
                }
                else
                {
                    return(IOContainer.Create(context, spread, container));
                }
            });

            RegisterInput(typeof(IDiffSpread <>), (factory, context) => {
                var attribute            = context.IOAttribute;
                var t                    = context.DataType;
                attribute.CheckIfChanged = true;
                ISpread spread           = null;

                if (t.IsGenericType && t.GetGenericArguments().Length == 1)
                {
                    if (typeof(ISpread <>).MakeGenericType(t.GetGenericArguments().First()).IsAssignableFrom(t))
                    {
                        var spreadType = typeof(DiffInputBinSpread <>).MakeGenericType(t.GetGenericArguments().First());

                        if (attribute.IsPinGroup)
                        {
                            spreadType = typeof(DiffInputSpreadList <>).MakeGenericType(t.GetGenericArguments().First());
                        }

                        spread = Activator.CreateInstance(spreadType, factory, attribute.Clone()) as ISpread;
                        if (attribute.AutoValidate)
                        {
                            return(GenericIOContainer.Create(context, factory, spread, s => s.Sync(), s => s.Flush()));
                        }
                        else
                        {
                            return(GenericIOContainer.Create(context, factory, spread, null, s => s.Flush()));
                        }
                    }
                }

                var container = factory.CreateIOContainer(typeof(IInStream <>).MakeGenericType(context.DataType), attribute, false);
                var pinType   = typeof(DiffInputPin <>).MakeGenericType(context.DataType);
                if (context.DataType == typeof(Matrix4x4))               //special diff pin for transform pins until IsChanged gets fixed in delphi
                {
                    spread = new DiffInputPin <Matrix4x4>(factory, container.GetPluginIO() as IPluginIn, new BufferedInputMatrix4x4IOStream(container.RawIOObject as IInStream <Matrix4x4>));
                }
                else if (context.DataType == typeof(Matrix))
                {
                    spread = new DiffInputPin <Matrix>(factory, container.GetPluginIO() as IPluginIn, new BufferedInputMatrixIOStream(container.RawIOObject as IInStream <Matrix>));
                }
                else
                {
                    spread = Activator.CreateInstance(pinType, factory, container.GetPluginIO(), container.RawIOObject) as ISpread;
                }
                if (attribute.AutoValidate)
                {
                    return(IOContainer.Create(context, spread, container, s => s.Sync()));
                }
                else
                {
                    return(IOContainer.Create(context, spread, container));
                }
            },
                          false);

            RegisterOutput(typeof(ISpread <>), (factory, context) => {
                var attribute = context.IOAttribute;
                var t         = context.DataType;
                if (t.IsGenericType && t.GetGenericArguments().Length == 1)
                {
                    if (typeof(ISpread <>).MakeGenericType(t.GetGenericArguments().First()).IsAssignableFrom(t))
                    {
                        var spreadType = typeof(OutputBinSpread <>).MakeGenericType(t.GetGenericArguments().First());

                        if (attribute.IsPinGroup)
                        {
                            spreadType = typeof(OutputSpreadList <>).MakeGenericType(t.GetGenericArguments().First());
                        }

                        ISpread spread;
                        if (context.BinSizeIOContainer != null)
                        {
                            spread = Activator.CreateInstance(spreadType, factory, attribute.Clone(), context.BinSizeIOContainer) as ISpread;
                        }
                        else
                        {
                            spread = Activator.CreateInstance(spreadType, factory, attribute.Clone()) as ISpread;
                        }
                        if (context.IOAttribute.AutoFlush)
                        {
                            return(GenericIOContainer.Create(context, factory, spread, null, s => s.Flush()));
                        }
                        else
                        {
                            return(GenericIOContainer.Create(context, factory, spread));
                        }
                    }
                }
                var container = factory.CreateIOContainer(typeof(IOutStream <>).MakeGenericType(context.DataType), attribute, false);
                var pinType   = typeof(OutputPin <>).MakeGenericType(context.DataType);
                var pin       = Activator.CreateInstance(pinType, factory, container.GetPluginIO(), container.RawIOObject) as ISpread;
                if (context.IOAttribute.AutoFlush)
                {
                    return(IOContainer.Create(context, pin, container, null, p => p.Flush()));
                }
                else
                {
                    return(IOContainer.Create(context, pin, container));
                }
            });

            RegisterConfig(typeof(IDiffSpread <>),
                           (factory, context) =>
            {
                var attribute = context.IOAttribute;
                var container = factory.CreateIOContainer(typeof(IIOStream <>).MakeGenericType(context.DataType), attribute, false);
                var pinType   = typeof(ConfigPin <>).MakeGenericType(context.DataType);
                var spread    = (IDiffSpread)Activator.CreateInstance(pinType, factory, container.GetPluginIO(), container.RawIOObject);
                return(IOContainer.Create(context, spread, container, null, s => s.Flush(), p => p.Sync()));
            },
                           true);
        }
Пример #7
0
        public PointerRegistry()
        {
            RegisterInput <FastValueInput>(
                (factory, context) =>
            {
                var t         = context.IOType;
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(IValueFastIn)));
                var stream    = Activator.CreateInstance(t, container.RawIOObject) as IInStream;

                if (context.IOAttribute.AutoValidate)
                {
                    return(IOContainer.Create(context, stream, container, s => s.Sync()));
                }
                else
                {
                    return(IOContainer.Create(context, stream, container));
                }
            });
            RegisterInput <ValueInput>(
                (factory, context) =>
            {
                var t         = context.IOType;
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(IValueFastIn)));
                var stream    = Activator.CreateInstance(t, container.RawIOObject) as IInStream;

                if (context.IOAttribute.AutoValidate)
                {
                    return(IOContainer.Create(context, stream, container, s => s.Sync()));
                }
                else
                {
                    return(IOContainer.Create(context, stream, container));
                }
            });

            RegisterOutput <ValueOutput>(
                (factory, context) =>
            {
                var t         = context.IOType;
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(IValueOut)));
                var stream    = Activator.CreateInstance(t, container.RawIOObject) as IOutStream;

                return(IOContainer.Create(context, stream, container));
            });

            RegisterInput <ColorInput>(
                (factory, context) =>
            {
                var t         = context.IOType;
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(IColorIn)));
                var stream    = Activator.CreateInstance(t, container.RawIOObject) as IOutStream;

                return(IOContainer.Create(context, stream, container));
            });

            RegisterOutput <ColorOutput>(
                (factory, context) =>
            {
                var t         = context.IOType;
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(IColorOut)));
                var stream    = Activator.CreateInstance(t, container.RawIOObject) as IOutStream;

                return(IOContainer.Create(context, stream, container));
            });

            RegisterInput <TransformInput>(
                (factory, context) =>
            {
                var t         = context.IOType;
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(ITransformIn)));
                var stream    = Activator.CreateInstance(t, container.RawIOObject) as IOutStream;

                return(IOContainer.Create(context, stream, container));
            });
            RegisterOutput <TransformOutput>(
                (factory, context) =>
            {
                var t         = context.IOType;
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(ITransformOut)));
                var stream    = Activator.CreateInstance(t, container.RawIOObject) as IOutStream;

                return(IOContainer.Create(context, stream, container));
            });

            //Plugin Interface version
            RegisterInput <IFastValuePointerInput>(
                (factory, context) =>
            {
                var t         = context.IOType;
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(IValueFastIn)));
                var stream    = Activator.CreateInstance(typeof(FastValueInput), container.RawIOObject) as IInStream;

                if (context.IOAttribute.AutoValidate)
                {
                    return(IOContainer.Create(context, stream, container, s => s.Sync()));
                }
                else
                {
                    return(IOContainer.Create(context, stream, container));
                }
            });
            RegisterInput <IValuePointerInput>(
                (factory, context) =>
            {
                var t         = context.IOType;
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(IValueFastIn)));
                var stream    = Activator.CreateInstance(typeof(ValueInput), container.RawIOObject) as IInStream;

                if (context.IOAttribute.AutoValidate)
                {
                    return(IOContainer.Create(context, stream, container, s => s.Sync()));
                }
                else
                {
                    return(IOContainer.Create(context, stream, container));
                }
            });

            RegisterOutput <IValuePointerOutput>(
                (factory, context) =>
            {
                var t         = context.IOType;
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(IValueOut)));
                var stream    = Activator.CreateInstance(typeof(ValueOutput), container.RawIOObject) as IOutStream;

                return(IOContainer.Create(context, stream, container));
            });

            RegisterInput <IColorPointerInput>(
                (factory, context) =>
            {
                var t         = context.IOType;
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(IColorIn)));
                var stream    = Activator.CreateInstance(typeof(ColorInput), container.RawIOObject) as IOutStream;

                return(IOContainer.Create(context, stream, container));
            });

            RegisterOutput <IColorPointerOutput>(
                (factory, context) =>
            {
                var t         = context.IOType;
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(IColorOut)));
                var stream    = Activator.CreateInstance(typeof(ColorOutput), container.RawIOObject) as IOutStream;

                return(IOContainer.Create(context, stream, container));
            });

            RegisterInput <ITransformPointerInput>(
                (factory, context) =>
            {
                var t         = context.IOType;
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(ITransformIn)));
                var stream    = Activator.CreateInstance(typeof(TransformInput), container.RawIOObject) as IInStream;

                return(IOContainer.Create(context, stream, container));
            });
            RegisterOutput <ITransformPointerOutput>(
                (factory, context) =>
            {
                var t         = context.IOType;
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(ITransformOut)));
                var stream    = Activator.CreateInstance(typeof(TransformOutput), container.RawIOObject) as IOutStream;

                return(IOContainer.Create(context, stream, container));
            });
        }
Пример #8
0
        public StreamRegistry()
        {
            int *       pLength;
            double **   ppDoubleData;
            float **    ppFloatData;
            Func <bool> validateFunc;



            RegisterInput(typeof(IInStream <double>), (factory, context) => {
                var container = GetValueContainer(factory, context, out pLength, out ppDoubleData, out validateFunc);
                var stream    = new DoubleInStream(pLength, ppDoubleData, validateFunc);
                return(IOContainer.Create(context, stream, container));
            });

            RegisterInput(typeof(IInStream <float>), (factory, context) => {
                var container = GetValueContainer(factory, context, out pLength, out ppDoubleData, out validateFunc);
                var stream    = new FloatInStream(pLength, ppDoubleData, validateFunc);
                return(IOContainer.Create(context, stream, container));
            });

            RegisterInput(typeof(IInStream <int>), (factory, context) => {
                var container = GetValueContainer(factory, context, out pLength, out ppDoubleData, out validateFunc);
                var stream    = new IntInStream(pLength, ppDoubleData, validateFunc);
                return(IOContainer.Create(context, stream, container));
            });

            RegisterInput(typeof(IInStream <uint>), (factory, context) => {
                var container = GetValueContainer(factory, context, out pLength, out ppDoubleData, out validateFunc);
                var stream    = new UIntInStream(pLength, ppDoubleData, validateFunc);
                return(IOContainer.Create(context, stream, container));
            });

            RegisterInput(typeof(IInStream <bool>), (factory, context) => {
                var container = GetValueContainer(factory, context, out pLength, out ppDoubleData, out validateFunc);
                var stream    = new BoolInStream(pLength, ppDoubleData, validateFunc);
                return(IOContainer.Create(context, stream, container));
            });

            RegisterInput(typeof(IInStream <Matrix4x4>), (factory, context) => {
                var container   = factory.CreateIOContainer(context.ReplaceIOType(typeof(ITransformIn)));
                var transformIn = container.RawIOObject as ITransformIn;
                transformIn.GetMatrixPointer(out pLength, out ppFloatData);
                var stream = new Matrix4x4InStream(pLength, (Matrix **)ppFloatData, GetValidateFunc(transformIn, context.IOAttribute.AutoValidate));
                return(IOContainer.Create(context, stream, container));
            });

            RegisterInput(typeof(IInStream <Matrix>), (factory, context) => {
                var container   = factory.CreateIOContainer(context.ReplaceIOType(typeof(ITransformIn)));
                var transformIn = container.RawIOObject as ITransformIn;
                transformIn.GetMatrixPointer(out pLength, out ppFloatData);
                var stream = new MatrixInStream(pLength, (Matrix **)ppFloatData, GetValidateFunc(transformIn, context.IOAttribute.AutoValidate));
                return(IOContainer.Create(context, stream, container));
            });

            RegisterInput(typeof(IInStream <Vector2D>), (factory, context) => {
                var container = GetValueContainer(factory, context, out pLength, out ppDoubleData, out validateFunc);
                var stream    = new Vector2DInStream(pLength, ppDoubleData, validateFunc);
                return(IOContainer.Create(context, stream, container));
            });
            RegisterInput(typeof(IInStream <Vector3D>), (factory, context) => {
                var container = GetValueContainer(factory, context, out pLength, out ppDoubleData, out validateFunc);
                var stream    = new Vector3DInStream(pLength, ppDoubleData, validateFunc);
                return(IOContainer.Create(context, stream, container));
            });
            RegisterInput(typeof(IInStream <Vector4D>), (factory, context) => {
                var container = GetValueContainer(factory, context, out pLength, out ppDoubleData, out validateFunc);
                var stream    = new Vector4DInStream(pLength, ppDoubleData, validateFunc);
                return(IOContainer.Create(context, stream, container));
            });

            RegisterInput(typeof(IInStream <Vector2>), (factory, context) => {
                var container = GetValueContainer(factory, context, out pLength, out ppDoubleData, out validateFunc);
                var stream    = new Vector2InStream(pLength, ppDoubleData, validateFunc);
                return(IOContainer.Create(context, stream, container));
            });
            RegisterInput(typeof(IInStream <Vector3>), (factory, context) => {
                var container = GetValueContainer(factory, context, out pLength, out ppDoubleData, out validateFunc);
                var stream    = new Vector3InStream(pLength, ppDoubleData, validateFunc);
                return(IOContainer.Create(context, stream, container));
            });
            RegisterInput(typeof(IInStream <Vector4>), (factory, context) => {
                var container = GetValueContainer(factory, context, out pLength, out ppDoubleData, out validateFunc);
                var stream    = new Vector4InStream(pLength, ppDoubleData, validateFunc);
                return(IOContainer.Create(context, stream, container));
            });

            RegisterInput(typeof(IInStream <Quaternion>), (factory, context) => {
                var container = GetValueContainer(factory, context, out pLength, out ppDoubleData, out validateFunc);
                var stream    = new QuaternionInStream(pLength, ppDoubleData, validateFunc);
                return(IOContainer.Create(context, stream, container));
            });

            RegisterInput(typeof(IInStream <RGBAColor>), (factory, context) => {
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(IColorIn)));
                var colorIn   = container.RawIOObject as IColorIn;
                colorIn.GetColorPointer(out pLength, out ppDoubleData);
                var stream = new ColorInStream(pLength, (RGBAColor **)ppDoubleData, GetValidateFunc(colorIn, context.IOAttribute.AutoValidate));
                return(IOContainer.Create(context, stream, container));
            });

            RegisterInput(typeof(IInStream <Color4>), (factory, context) => {
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(IColorIn)));
                var colorIn   = container.RawIOObject as IColorIn;
                colorIn.GetColorPointer(out pLength, out ppDoubleData);
                var stream = new SlimDXColorInStream(pLength, (RGBAColor **)ppDoubleData, GetValidateFunc(colorIn, context.IOAttribute.AutoValidate));
                return(IOContainer.Create(context, stream, container));
            });

            RegisterInput <MemoryIOStream <string> >(
                (factory, context) =>
            {
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(IStringIn)));
                var stringIn  = container.RawIOObject as IStringIn;
                var stream    = new StringInStream(stringIn);
                // Using MemoryIOStream -> needs to be synced on managed side.
                if (context.IOAttribute.AutoValidate)
                {
                    return(IOContainer.Create(context, stream, container, s => s.Sync()));
                }
                else
                {
                    return(IOContainer.Create(context, stream, container));
                }
            });

            RegisterInput <MemoryIOStream <System.IO.Stream> >(
                (factory, context) =>
            {
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(IRawIn)));
                var rawIn     = container.RawIOObject as IRawIn;
                var stream    = new RawInStream(rawIn);
                // Using MemoryIOStream -> needs to be synced on managed side.
                if (context.IOAttribute.AutoValidate)
                {
                    return(IOContainer.Create(context, stream, container, s => s.Sync()));
                }
                else
                {
                    return(IOContainer.Create(context, stream, container));
                }
            });

            RegisterInput <MemoryIOStream <EnumEntry> >(
                (factory, context) =>
            {
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(IEnumIn)));
                var enumIn    = container.RawIOObject as IEnumIn;
                var stream    = new DynamicEnumInStream(enumIn, context.IOAttribute.EnumName);
                // Using MemoryIOStream -> needs to be synced on managed side.
                if (context.IOAttribute.AutoValidate)
                {
                    return(IOContainer.Create(context, stream, container, s => s.Sync()));
                }
                else
                {
                    return(IOContainer.Create(context, stream, container));
                }
            });

            // InputIOStream can fullfill this contract a little more memory efficient than BufferedIOStream
            RegisterInput(typeof(IIOStream <>),
                          (factory, context) =>
            {
                var inStreamType = typeof(IInStream <>).MakeGenericType(context.DataType);
                var ioStreamType = typeof(InputIOStream <>).MakeGenericType(context.DataType);
                var container    = factory.CreateIOContainer(context.ReplaceIOType(inStreamType));
                var ioStream     = (IIOStream)Activator.CreateInstance(ioStreamType, container.RawIOObject);
                if (context.IOAttribute.AutoValidate)
                {
                    return(IOContainer.Create(context, ioStream, container, s => s.Sync(), s => s.Flush()));
                }
                else
                {
                    return(IOContainer.Create(context, ioStream, container, null, s => s.Flush()));
                }
            },
                          false);

            RegisterInput(typeof(IInStream <>), (factory, context) => {
                var t         = context.DataType;
                var attribute = context.IOAttribute;
                if (t.IsGenericType && t.GetGenericArguments().Length == 1)
                {
                    if (typeof(IInStream <>).MakeGenericType(t.GetGenericArguments().First()).IsAssignableFrom(t))
                    {
                        var multiDimStreamType = typeof(MultiDimInStream <>).MakeGenericType(t.GetGenericArguments().First());
                        if (attribute.IsPinGroup)
                        {
                            multiDimStreamType = typeof(GroupInStream <>).MakeGenericType(t.GetGenericArguments().First());
                        }

                        var stream = Activator.CreateInstance(multiDimStreamType, factory, attribute.Clone()) as IInStream;

                        // PinGroup implementation doesn't need to get synced on managed side.
                        if (!attribute.IsPinGroup && attribute.AutoValidate)
                        {
                            return(GenericIOContainer.Create(context, factory, stream, s => s.Sync()));
                        }
                        else
                        {
                            return(GenericIOContainer.Create(context, factory, stream));
                        }
                    }
                }

                {
                    IIOContainer container;
                    IInStream stream;
                    if (context.DataType == typeof(MouseState))
                    {
                        context   = context.ReplaceDataType(typeof(Mouse));
                        container = factory.CreateIOContainer(context.ReplaceIOType(typeof(INodeIn)));
                        stream    = Activator.CreateInstance(typeof(MouseToMouseStateInStream), container.RawIOObject) as IInStream;
                    }
                    else if (context.DataType == typeof(KeyboardState))
                    {
                        context   = context.ReplaceDataType(typeof(Keyboard));
                        container = factory.CreateIOContainer(context.ReplaceIOType(typeof(INodeIn)));
                        stream    = Activator.CreateInstance(typeof(KeyboardToKeyboardStateInStream), container.RawIOObject) as IInStream;
                    }
                    else
                    {
                        container = factory.CreateIOContainer(context.ReplaceIOType(typeof(INodeIn)));
                        stream    = Activator.CreateInstance(typeof(NodeInStream <>).MakeGenericType(context.DataType), container.RawIOObject) as IInStream;
                    }
                    // Using MemoryIOStream -> needs to be synced on managed side.
                    if (attribute.AutoValidate)
                    {
                        return(IOContainer.Create(context, stream, container, s => s.Sync()));
                    }
                    else
                    {
                        return(IOContainer.Create(context, stream, container));
                    }
                }
            });

            RegisterOutput(typeof(IOutStream <double>), (factory, context) => {
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(IValueOut)));
                var valueOut  = container.RawIOObject as IValueOut;
                valueOut.GetValuePointer(out ppDoubleData);
                return(IOContainer.Create(context, new DoubleOutStream(ppDoubleData, GetSetValueLengthAction(valueOut)), container));
            });

            RegisterOutput(typeof(IOutStream <float>), (factory, context) => {
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(IValueOut)));
                var valueOut  = container.RawIOObject as IValueOut;
                valueOut.GetValuePointer(out ppDoubleData);
                return(IOContainer.Create(context, new FloatOutStream(ppDoubleData, GetSetValueLengthAction(valueOut)), container));
            });

            RegisterOutput(typeof(IOutStream <int>), (factory, context) => {
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(IValueOut)));
                var valueOut  = container.RawIOObject as IValueOut;
                valueOut.GetValuePointer(out ppDoubleData);
                return(IOContainer.Create(context, new IntOutStream(ppDoubleData, GetSetValueLengthAction(valueOut)), container));
            });

            RegisterOutput(typeof(IOutStream <uint>), (factory, context) => {
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(IValueOut)));
                var valueOut  = container.RawIOObject as IValueOut;
                valueOut.GetValuePointer(out ppDoubleData);
                return(IOContainer.Create(context, new UIntOutStream(ppDoubleData, GetSetValueLengthAction(valueOut)), container));
            });

            RegisterOutput(typeof(IOutStream <bool>), (factory, context) => {
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(IValueOut)));
                var valueOut  = container.RawIOObject as IValueOut;
                valueOut.GetValuePointer(out ppDoubleData);
                return(IOContainer.Create(context, new BoolOutStream(ppDoubleData, GetSetValueLengthAction(valueOut)), container));
            });

            RegisterOutput(typeof(IOutStream <Matrix4x4>), (factory, context) => {
                var container    = factory.CreateIOContainer(context.ReplaceIOType(typeof(ITransformOut)));
                var transformOut = container.RawIOObject as ITransformOut;
                transformOut.GetMatrixPointer(out ppFloatData);
                return(IOContainer.Create(context, new Matrix4x4OutStream((Matrix **)ppFloatData, GetSetMatrixLengthAction(transformOut)), container));
            });

            RegisterOutput(typeof(IOutStream <Matrix>), (factory, context) => {
                var container    = factory.CreateIOContainer(context.ReplaceIOType(typeof(ITransformOut)));
                var transformOut = container.RawIOObject as ITransformOut;
                transformOut.GetMatrixPointer(out ppFloatData);
                return(IOContainer.Create(context, new MatrixOutStream((Matrix **)ppFloatData, GetSetMatrixLengthAction(transformOut)), container));
            });

            RegisterOutput(typeof(IOutStream <Vector2D>), (factory, context) => {
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(IValueOut)));
                var valueOut  = container.RawIOObject as IValueOut;
                valueOut.GetValuePointer(out ppDoubleData);
                return(IOContainer.Create(context, new Vector2DOutStream(ppDoubleData, GetSetValueLengthAction(valueOut)), container));
            });
            RegisterOutput(typeof(IOutStream <Vector3D>), (factory, context) => {
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(IValueOut)));
                var valueOut  = container.RawIOObject as IValueOut;
                valueOut.GetValuePointer(out ppDoubleData);
                return(IOContainer.Create(context, new Vector3DOutStream(ppDoubleData, GetSetValueLengthAction(valueOut)), container));
            });
            RegisterOutput(typeof(IOutStream <Vector4D>), (factory, context) => {
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(IValueOut)));
                var valueOut  = container.RawIOObject as IValueOut;
                valueOut.GetValuePointer(out ppDoubleData);
                return(IOContainer.Create(context, new Vector4DOutStream(ppDoubleData, GetSetValueLengthAction(valueOut)), container));
            });

            RegisterOutput(typeof(IOutStream <Vector2>), (factory, context) => {
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(IValueOut)));
                var valueOut  = container.RawIOObject as IValueOut;
                valueOut.GetValuePointer(out ppDoubleData);
                return(IOContainer.Create(context, new Vector2OutStream(ppDoubleData, GetSetValueLengthAction(valueOut)), container));
            });
            RegisterOutput(typeof(IOutStream <Vector3>), (factory, context) => {
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(IValueOut)));
                var valueOut  = container.RawIOObject as IValueOut;
                valueOut.GetValuePointer(out ppDoubleData);
                return(IOContainer.Create(context, new Vector3OutStream(ppDoubleData, GetSetValueLengthAction(valueOut)), container));
            });
            RegisterOutput(typeof(IOutStream <Vector4>), (factory, context) => {
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(IValueOut)));
                var valueOut  = container.RawIOObject as IValueOut;
                valueOut.GetValuePointer(out ppDoubleData);
                return(IOContainer.Create(context, new Vector4OutStream(ppDoubleData, GetSetValueLengthAction(valueOut)), container));
            });

            RegisterOutput(typeof(IOutStream <Quaternion>), (factory, context) => {
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(IValueOut)));
                var valueOut  = container.RawIOObject as IValueOut;
                valueOut.GetValuePointer(out ppDoubleData);
                return(IOContainer.Create(context, new QuaternionOutStream(ppDoubleData, GetSetValueLengthAction(valueOut)), container));
            });

            RegisterOutput(typeof(IOutStream <RGBAColor>), (factory, context) => {
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(IColorOut)));
                var colorOut  = container.RawIOObject as IColorOut;
                colorOut.GetColorPointer(out ppDoubleData);
                return(IOContainer.Create(context, new ColorOutStream((RGBAColor **)ppDoubleData, GetSetColorLengthAction(colorOut)), container));
            });

            RegisterOutput(typeof(IOutStream <Color4>), (factory, context) => {
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(IColorOut)));
                var colorOut  = container.RawIOObject as IColorOut;
                colorOut.GetColorPointer(out ppDoubleData);
                return(IOContainer.Create(context, new SlimDXColorOutStream((RGBAColor **)ppDoubleData, GetSetColorLengthAction(colorOut)), container));
            });

            RegisterOutput(typeof(IOutStream <EnumEntry>), (factory, context) => {
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(IEnumOut)));
                var enumOut   = container.RawIOObject as IEnumOut;
                if (context.IOAttribute.AutoFlush)
                {
                    return(IOContainer.Create(context, new DynamicEnumOutStream(enumOut), container, null, s => s.Flush()));
                }
                else
                {
                    return(IOContainer.Create(context, new DynamicEnumOutStream(enumOut), container));
                }
            });

            RegisterOutput <IOutStream <System.IO.Stream> >(
                (factory, context) =>
            {
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(IRawOut)));
                var rawOut    = container.RawIOObject as IRawOut;
                if (context.IOAttribute.AutoFlush)
                {
                    return(IOContainer.Create(context, new RawOutStream(rawOut), container, null, s => s.Flush()));
                }
                else
                {
                    return(IOContainer.Create(context, new RawOutStream(rawOut), container));
                }
            });

            RegisterOutput <MemoryIOStream <string> >(
                (factory, context) =>
            {
                var container = factory.CreateIOContainer(context.ReplaceIOType(typeof(IStringOut)));
                var stringOut = container.RawIOObject as IStringOut;
                if (context.IOAttribute.AutoFlush)
                {
                    return(IOContainer.Create(context, new StringOutStream(stringOut), container, null, s => s.Flush()));
                }
                else
                {
                    return(IOContainer.Create(context, new StringOutStream(stringOut), container));
                }
            });

            RegisterOutput(typeof(IOutStream <>), (factory, context) => {
                var host      = factory.PluginHost;
                var t         = context.DataType;
                var attribute = context.IOAttribute;
                if (t.IsGenericType)
                {
                    var genericArguments = t.GetGenericArguments();
                    Type streamType      = null;
                    switch (genericArguments.Length)
                    {
                    case 1:
                        if (typeof(IInStream <>).MakeGenericType(genericArguments).IsAssignableFrom(t))
                        {
                            var multiDimStreamType = typeof(MultiDimOutStream <>).MakeGenericType(t.GetGenericArguments().First());
                            var stream             = Activator.CreateInstance(multiDimStreamType, factory, attribute.Clone()) as IOutStream;
                            if (context.IOAttribute.AutoFlush)
                            {
                                return(GenericIOContainer.Create(context, factory, stream, null, s => s.Flush()));
                            }
                            else
                            {
                                return(GenericIOContainer.Create(context, factory, stream));
                            }
                        }
                        try
                        {
                            if (typeof(TextureResource <>).MakeGenericType(genericArguments).IsAssignableFrom(t))
                            {
                                var metadataType = genericArguments[0];
                                streamType       = typeof(TextureOutStream <,>);
                                streamType       = streamType.MakeGenericType(t, metadataType);
                            }
                        }
                        catch (ArgumentException)
                        {
                            // Type constraints weren't satisfied.
                            streamType = null;
                        }
                        try
                        {
                            if (typeof(MeshResource <>).MakeGenericType(genericArguments).IsAssignableFrom(t))
                            {
                                var metadataType = genericArguments[0];
                                streamType       = typeof(MeshOutStream <,>);
                                streamType       = streamType.MakeGenericType(t, metadataType);
                            }
                        }
                        catch (ArgumentException)
                        {
                            // Type constraints weren't satisfied.
                            streamType = null;
                        }
                        if (streamType != null)
                        {
                            var stream = Activator.CreateInstance(streamType, host, attribute) as IOutStream;
                            if (context.IOAttribute.AutoFlush)
                            {
                                return(GenericIOContainer.Create(context, factory, stream, null, s => s.Flush()));
                            }
                            else
                            {
                                return(GenericIOContainer.Create(context, factory, stream));
                            }
                        }
                        break;

                    case 2:
                        try
                        {
                            if (typeof(DXResource <,>).MakeGenericType(genericArguments).IsAssignableFrom(t))
                            {
                                var resourceType = genericArguments[0];
                                var metadataType = genericArguments[1];
                                if (resourceType == typeof(Texture))
                                {
                                    streamType = typeof(TextureOutStream <,>);
                                    streamType = streamType.MakeGenericType(t, metadataType);
                                }
                                else if (resourceType == typeof(Mesh))
                                {
                                    streamType = typeof(MeshOutStream <,>);
                                    streamType = streamType.MakeGenericType(t, metadataType);
                                }
                                if (streamType != null)
                                {
                                    var stream = Activator.CreateInstance(streamType, host, attribute) as IOutStream;
                                    if (context.IOAttribute.AutoFlush)
                                    {
                                        return(GenericIOContainer.Create(context, factory, stream, null, s => s.Flush()));
                                    }
                                    else
                                    {
                                        return(GenericIOContainer.Create(context, factory, stream));
                                    }
                                }
                                else
                                {
                                    throw new NotImplementedException();
                                }
                            }
                        }
                        catch (ArgumentException)
                        {
                            // Type constraints weren't satisfied.
                        }
                        break;
                    }
                }

                {
                    IOutStream stream;
                    IIOContainer container;
                    if (context.DataType == typeof(MouseState))
                    {
                        context   = context.ReplaceDataType(typeof(Mouse));
                        container = factory.CreateIOContainer(context.ReplaceIOType(typeof(INodeOut)));
                        stream    = Activator.CreateInstance(typeof(MouseStateToMouseOutStream), container.RawIOObject) as IOutStream;
                    }
                    else if (context.DataType == typeof(KeyboardState))
                    {
                        context   = context.ReplaceDataType(typeof(Keyboard));
                        container = factory.CreateIOContainer(context.ReplaceIOType(typeof(INodeOut)));
                        stream    = Activator.CreateInstance(typeof(KeyboardStateToKeyboardOutStream), container.RawIOObject) as IOutStream;
                    }
                    else
                    {
                        container = factory.CreateIOContainer(context.ReplaceIOType(typeof(INodeOut)));
                        stream    = Activator.CreateInstance(typeof(NodeOutStream <>).MakeGenericType(context.DataType), container.RawIOObject) as IOutStream;
                    }
                    if (context.IOAttribute.AutoFlush)
                    {
                        return(IOContainer.Create(context, stream, container, null, s => s.Flush()));
                    }
                    else
                    {
                        return(IOContainer.Create(context, stream, container));
                    }
                }
            });

            RegisterOutput(typeof(IInStream <>), (factory, context) => {
                var t         = context.DataType;
                var attribute = context.IOAttribute;
                if (t.IsGenericType)
                {
                    if (typeof(IOutStream <>).MakeGenericType(t.GetGenericArguments()).IsAssignableFrom(t))
                    {
                        var multiDimStreamType = typeof(GroupOutStream <>).MakeGenericType(t.GetGenericArguments().First());
                        if (!attribute.IsPinGroup)
                        {
                            throw new NotSupportedException("IInStream<IOutStream<T>> can only be used as a pin group.");
                        }

                        var stream = Activator.CreateInstance(multiDimStreamType, factory, attribute.Clone()) as IFlushable;
                        if (context.IOAttribute.AutoFlush)
                        {
                            return(GenericIOContainer.Create(context, factory, stream, null, s => s.Flush()));
                        }
                        else
                        {
                            return(GenericIOContainer.Create(context, factory, stream));
                        }
                    }
                }

                return(null);               // IOFactory will throw a NotSupportedException with a few more details.
            });

            RegisterOutput(typeof(IIOStream <>), (factory, context) => {
                var outStreamType = typeof(IOutStream <>).MakeGenericType(context.DataType);
                var ioStreamType  = typeof(BufferedOutputIOStream <>).MakeGenericType(context.DataType);
                var container     = factory.CreateIOContainer(outStreamType, context.IOAttribute, false);
                var ioStream      = (IIOStream)Activator.CreateInstance(ioStreamType, container.RawIOObject);
                if (context.IOAttribute.AutoFlush)
                {
                    return(IOContainer.Create(context, ioStream, container, null, s => s.Flush()));
                }
                else
                {
                    return(IOContainer.Create(context, ioStream, container));
                }
            },
                           false);

            RegisterConfig(typeof(MemoryIOStream <Vector2>), (factory, context) =>
            {
                var container   = factory.CreateIOContainer(context.ReplaceIOType(typeof(IValueConfig)));
                var valueConfig = container.RawIOObject as IValueConfig;
                var stream      = new Vector2ConfigStream(valueConfig);
                return(IOContainer.Create(context, stream, container, null, s => s.Flush(), s => s.Sync()));
            });
            RegisterConfig(typeof(MemoryIOStream <Vector3>), (factory, context) =>
            {
                var container   = factory.CreateIOContainer(context.ReplaceIOType(typeof(IValueConfig)));
                var valueConfig = container.RawIOObject as IValueConfig;
                var stream      = new Vector3ConfigStream(valueConfig);
                return(IOContainer.Create(context, stream, container, null, s => s.Flush(), s => s.Sync()));
            });
            RegisterConfig(typeof(MemoryIOStream <Vector4>), (factory, context) =>
            {
                var container   = factory.CreateIOContainer(context.ReplaceIOType(typeof(IValueConfig)));
                var valueConfig = container.RawIOObject as IValueConfig;
                var stream      = new Vector4ConfigStream(valueConfig);
                return(IOContainer.Create(context, stream, container, null, s => s.Flush(), s => s.Sync()));
            });



            RegisterConfig(typeof(MemoryIOStream <Quaternion>), (factory, context) =>
            {
                var container   = factory.CreateIOContainer(context.ReplaceIOType(typeof(IValueConfig)));
                var valueConfig = container.RawIOObject as IValueConfig;
                var stream      = new QuaternionConfigStream(valueConfig);
                return(IOContainer.Create(context, stream, container, null, s => s.Flush(), s => s.Sync()));
            });



            RegisterConfig(typeof(MemoryIOStream <Vector2D>), (factory, context) =>
            {
                var container   = factory.CreateIOContainer(context.ReplaceIOType(typeof(IValueConfig)));
                var valueConfig = container.RawIOObject as IValueConfig;
                var stream      = new Vector2DConfigStream(valueConfig);
                return(IOContainer.Create(context, stream, container, null, s => s.Flush(), s => s.Sync()));
            });
            RegisterConfig(typeof(MemoryIOStream <Vector3D>), (factory, context) =>
            {
                var container   = factory.CreateIOContainer(context.ReplaceIOType(typeof(IValueConfig)));
                var valueConfig = container.RawIOObject as IValueConfig;
                var stream      = new Vector3DConfigStream(valueConfig);
                return(IOContainer.Create(context, stream, container, null, s => s.Flush(), s => s.Sync()));
            });
            RegisterConfig(typeof(MemoryIOStream <Vector4D>), (factory, context) =>
            {
                var container   = factory.CreateIOContainer(context.ReplaceIOType(typeof(IValueConfig)));
                var valueConfig = container.RawIOObject as IValueConfig;
                var stream      = new Vector4DConfigStream(valueConfig);
                return(IOContainer.Create(context, stream, container, null, s => s.Flush(), s => s.Sync()));
            });

            RegisterConfig(typeof(MemoryIOStream <string>), (factory, context) => {
                var container    = factory.CreateIOContainer(context.ReplaceIOType(typeof(IStringConfig)));
                var stringConfig = container.RawIOObject as IStringConfig;
                var stream       = new StringConfigStream(stringConfig);
                return(IOContainer.Create(context, stream, container, null, s => s.Flush(), s => s.Sync()));
            });

            RegisterConfig(typeof(MemoryIOStream <RGBAColor>), (factory, context) => {
                var container   = factory.CreateIOContainer(context.ReplaceIOType(typeof(IColorConfig)));
                var colorConfig = container.RawIOObject as IColorConfig;
                var stream      = new ColorConfigStream(colorConfig);
                return(IOContainer.Create(context, stream, container, null, s => s.Flush(), s => s.Sync()));
            });

            RegisterConfig(typeof(MemoryIOStream <Color4>), (factory, context) => {
                var container   = factory.CreateIOContainer(context.ReplaceIOType(typeof(IColorConfig)));
                var colorConfig = container.RawIOObject as IColorConfig;
                var stream      = new SlimDXColorConfigStream(colorConfig);
                return(IOContainer.Create(context, stream, container, null, s => s.Flush(), s => s.Sync()));
            });

            RegisterConfig(typeof(MemoryIOStream <EnumEntry>), (factory, context) => {
                var container  = factory.CreateIOContainer(context.ReplaceIOType(typeof(IEnumConfig)));
                var enumConfig = container.RawIOObject as IEnumConfig;
                var stream     = new DynamicEnumConfigStream(enumConfig, context.IOAttribute.EnumName);
                return(IOContainer.Create(context, stream, container, null, s => s.Flush(), s => s.Sync()));
            });
            RegisterConfig(typeof(MemoryIOStream <>), (factory, context) => {
                var t = context.DataType;
                if (t.IsPrimitive)
                {
                    var container   = factory.CreateIOContainer(context.ReplaceIOType(typeof(IValueConfig)));
                    var valueConfig = container.RawIOObject as IValueConfig;
                    var streamType  = typeof(ValueConfigStream <>).MakeGenericType(context.DataType);
                    var stream      = Activator.CreateInstance(streamType, new object[] { valueConfig }) as IIOStream;
                    return(IOContainer.Create(context, stream, container, null, s => s.Flush(), s => s.Sync()));
                }
                throw new NotSupportedException(string.Format("Config pin of type '{0}' is not supported.", t));
            });
        }
Пример #9
0
        public SpreadRegistry()
        {
            RegisterInput(typeof(ISpread <>), (factory, context) => {
                var attribute  = context.IOAttribute;
                var t          = context.DataType;
                ISpread spread = null;
                if (t.IsGenericType && t.GetGenericArguments().Length == 1)
                {
                    if (typeof(ISpread <>).MakeGenericType(t.GetGenericArguments().First()).IsAssignableFrom(t))
                    {
                        var spreadType = typeof(InputBinSpread <>).MakeGenericType(t.GetGenericArguments().First());

                        if (attribute.IsPinGroup)
                        {
                            spreadType = typeof(InputSpreadList <>).MakeGenericType(t.GetGenericArguments().First());
                        }

                        spread = Activator.CreateInstance(spreadType, factory, attribute.Clone()) as ISpread;
                        if (attribute.AutoValidate)
                        {
                            return(GenericIOContainer.Create(context, factory, spread, s => s.Sync()));
                        }
                        else
                        {
                            return(GenericIOContainer.Create(context, factory, spread));
                        }
                    }
                }
                var container = factory.CreateIOContainer(typeof(IInStream <>).MakeGenericType(context.DataType), attribute, false);
                var pinType   = typeof(InputPin <>).MakeGenericType(context.DataType);
                spread        = Activator.CreateInstance(pinType, factory, container.GetPluginIO(), container.RawIOObject) as ISpread;
                if (attribute.AutoValidate)
                {
                    return(IOContainer.Create(context, spread, container, p => p.Sync()));
                }
                else
                {
                    return(IOContainer.Create(context, spread, container));
                }
            });

            RegisterInput(typeof(IDiffSpread <>), (factory, context) => {
                var attribute            = context.IOAttribute;
                var t                    = context.DataType;
                attribute.CheckIfChanged = true;
                ISpread spread           = null;

                if (t.IsGenericType && t.GetGenericArguments().Length == 1)
                {
                    if (typeof(ISpread <>).MakeGenericType(t.GetGenericArguments().First()).IsAssignableFrom(t))
                    {
                        var spreadType = typeof(DiffInputBinSpread <>).MakeGenericType(t.GetGenericArguments().First());

                        if (attribute.IsPinGroup)
                        {
                            spreadType = typeof(DiffInputSpreadList <>).MakeGenericType(t.GetGenericArguments().First());
                        }

                        spread = Activator.CreateInstance(spreadType, factory, attribute.Clone()) as ISpread;
                        if (attribute.AutoValidate)
                        {
                            return(GenericIOContainer.Create(context, factory, spread, s => s.Sync(), s => s.Flush()));
                        }
                        else
                        {
                            return(GenericIOContainer.Create(context, factory, spread, null, s => s.Flush()));
                        }
                    }
                }
                var container = factory.CreateIOContainer(typeof(IInStream <>).MakeGenericType(context.DataType), attribute, false);
                var pinType   = typeof(DiffInputPin <>).MakeGenericType(context.DataType);
                spread        = Activator.CreateInstance(pinType, factory, container.GetPluginIO(), container.RawIOObject) as ISpread;
                if (attribute.AutoValidate)
                {
                    return(IOContainer.Create(context, spread, container, s => s.Sync()));
                }
                else
                {
                    return(IOContainer.Create(context, spread, container));
                }
            },
                          false);

            RegisterOutput(typeof(ISpread <>), (factory, context) => {
                var attribute = context.IOAttribute;
                var t         = context.DataType;
                if (t.IsGenericType && t.GetGenericArguments().Length == 1)
                {
                    if (typeof(ISpread <>).MakeGenericType(t.GetGenericArguments().First()).IsAssignableFrom(t))
                    {
                        var spreadType = typeof(OutputBinSpread <>).MakeGenericType(t.GetGenericArguments().First());

                        if (attribute.IsPinGroup)
                        {
                            spreadType = typeof(OutputSpreadList <>).MakeGenericType(t.GetGenericArguments().First());
                        }

                        var spread = Activator.CreateInstance(spreadType, factory, attribute.Clone()) as ISpread;
                        return(GenericIOContainer.Create(context, factory, spread, null, s => s.Flush()));
                    }
                }
                var container = factory.CreateIOContainer(typeof(IOutStream <>).MakeGenericType(context.DataType), attribute, false);
                var pinType   = typeof(OutputPin <>).MakeGenericType(context.DataType);
                var pin       = Activator.CreateInstance(pinType, factory, container.GetPluginIO(), container.RawIOObject) as ISpread;
                return(IOContainer.Create(context, pin, container, null, p => p.Flush()));
            });

            RegisterConfig(typeof(IDiffSpread <>),
                           (factory, context) =>
            {
                var attribute = context.IOAttribute;
                var container = factory.CreateIOContainer(typeof(IIOStream <>).MakeGenericType(context.DataType), attribute, false);
                var pinType   = typeof(ConfigPin <>).MakeGenericType(context.DataType);
                var spread    = (IDiffSpread)Activator.CreateInstance(pinType, factory, container.GetPluginIO(), container.RawIOObject);
                return(IOContainer.Create(context, spread, container, null, s => s.Flush(), p => p.Sync()));
            },
                           true);
        }