Beispiel #1
0
        internal void ProcessQuadRenderCommand(CCQuadCommand quadCommand)
        {
            var worldTransform = quadCommand.WorldTransform;
            var identity       = worldTransform == CCAffineTransform.Identity;

            quadCommands.Add(quadCommand);

            var quads = quadCommand.Quads;

            for (int i = 0, N = quadCommand.QuadCount; i < N; ++i)
            {
                if (identity)
                {
                    currentBatchedQuads.Add(quads[i]);
                }
                else
                {
                    currentBatchedQuads.Add(worldTransform.Transform(quads[i]));
                }
            }

            // We're changing command types so render any pending sequence of commandss
            // e.g. Batched quad commands
            if ((currentCommandType & CCCommandType.Quad) == CCCommandType.None)
            {
                Flush();
            }

            currentCommandType = CCCommandType.Quad;
        }
Beispiel #2
0
        // See http://slabode.exofire.net/circle_draw.shtml
        // An Efficient Way to Draw Approximate Circles in OpenGL
        // Try to keep from calculating Cos and Sin of values everytime and just use
        // add and subtract where possible to calculate the values.
        public void DrawCircle(CCPoint pos, float radius, CCColor4B color)
        {
            var cl = color.ToColor();

            int segments = (int)(10 * (float)Math.Sqrt(radius));  //<- Let's try to guess at # segments for a reasonable smoothness

            float theta            = MathHelper.Pi * 2.0f / segments;
            float tangetial_factor = (float)Math.Tan(theta); //calculate the tangential factor

            float radial_factor = (float)Math.Cos(theta);    //calculate the radial factor

            float x = radius;                                //we start at angle = 0
            float y = 0;

            var   verticeCenter = new VertexPositionColor(new Vector3(pos.X, pos.Y, 0), cl);
            var   vert1         = new VertexPositionColor(Vector3.Zero, cl);
            float tx            = 0;
            float ty            = 0;

            for (int i = 0; i < segments; i++)
            {
                vert1.Position.X = x + pos.X;
                vert1.Position.Y = y + pos.Y;
                lineVertices.Add(vert1); // output vertex

                //calculate the tangential vector
                //remember, the radial vector is (x, y)
                //to get the tangential vector we flip those coordinates and negate one of them
                tx = -y;
                ty = x;

                //add the tangential vector
                x += tx * tangetial_factor;
                y += ty * tangetial_factor;

                //correct using the radial factor
                x *= radial_factor;
                y *= radial_factor;

                vert1.Position.X = x + pos.X;
                vert1.Position.Y = y + pos.Y;
                lineVertices.Add(vert1); // output vertex
            }

            dirty = true;
        }
Beispiel #3
0
        public void AddTargetWithActionForControlEvent(object target, Action <object, CCControlEvent> action, CCControlEvent controlEvent)
        {
            // Create the invocation object
            var invocation = new CCInvocation(target, action, controlEvent);

            // Add the invocation into the dispatch list for the given control event
            CCRawList <CCInvocation> eventInvocationList = DispatchListforControlEvent(controlEvent);

            eventInvocationList.Add(invocation);
        }
Beispiel #4
0
        void ExecuteRenderCommand(CCRenderCommand command)
        {
            if (command is CCQuadCommand)
            {
                Flush3D();
                FlushTriangles();

                //Console.WriteLine(((CCQuadCommand)command).QuadCount);
                var quadCommand = (CCQuadCommand)command;

                var drawManager = DrawManager;

                //Draw batched quads if necessary
                // TODO: Check for buffer size
                if (command.IsSkipBatching) // || (numberQuads + cmd->getQuadCount()) * 4 > VBO_SIZE )
                {
                    // TODO: Check for buffer size
                    //CCASSERT(cmd->getQuadCount()>= 0 && cmd->getQuadCount() * 4 < VBO_SIZE, "VBO for vertex is not big enough, please break the data down or use customized render command");

                    //Draw batched quads if VBO is full
                    DrawBatchedQuads();
                }

                var mv = command.ModelViewTransform;

                batchQuadCommands.Add(quadCommand);

                for (int b = 0; b < quadCommand.QuadCount; b++)
                {
                    quads.Add(mv.Transform(quadCommand.Quads[b]));
                }
                numberQuads += quadCommand.QuadCount;

                if (quadCommand.IsSkipBatching)
                {
                    DrawBatchedQuads();
                }
            }
            else
            {
                Flush();
                command.Execute(DrawManager);
            }
        }
        void FlushLines()
        {
            if (!hasBegun)
            {
                throw new InvalidOperationException("Begin must be called before Flush can be called.");
            }

            if (lineVertsCount >= 2)
            {
                int primitiveCount = lineVertsCount / 2;

                var lines = new CCV3F_C4B[lineVertsCount];
                Array.Copy(lineVertices, lines, triangleVertsCount);
                // add the Line Lists to our line list vertices for later rendering from the Renderer
                lineVerts.Add(lines);

                lineVertsCount -= primitiveCount * 2;
            }
        }
        void FlushTriangles()
        {
            if (!hasBegun)
            {
                throw new InvalidOperationException("Begin must be called before Flush can be called.");
            }

            if (triangleVertsCount >= 3)
            {
                int primitiveCount = triangleVertsCount / 3;

                var triangles = new CCV3F_C4B[triangleVertsCount];
                Array.Copy(triangleVertices, triangles, triangleVertsCount);
                // add the Triangle List to our triangles list vertices for later rendering from the Renderer
                triangleVerts.Add(triangles);

                triangleVertsCount -= primitiveCount * 3;
            }
        }
Beispiel #7
0
        public CCGeometryInstance CreateGeometryInstance(int numberOfVertices, int numberOfIndicies)
        {
            var item = new CCGeometryInstance();

            if (item.GeometryPacket.Vertices.Length < numberOfVertices)
            {
                item.GeometryPacket.Vertices = new CCV3F_C4B_T2F[numberOfVertices];
            }

            if (item.GeometryPacket.Indicies.Length < numberOfIndicies)
            {
                item.GeometryPacket.Indicies = new int[numberOfIndicies];
            }

            item.GeometryPacket.NumberOfVertices = numberOfVertices;
            item.GeometryPacket.NumberOfIndicies = numberOfIndicies;

            batchItemList.Add(item);

            return(item);
        }
Beispiel #8
0
        public CCGeometryInstance CreateGeometryInstance(int numberOfVertices, int numberOfIndicies, PrimitiveType primitiveType = PrimitiveType.TriangleList)
        {
            var item = new CCGeometryInstance();

            item.InstanceAttributes.PrimitiveType = primitiveType;

            if (item.GeometryPacket.Vertices.Length < numberOfVertices)
            {
                item.GeometryPacket.Vertices = new CCV3F_C4B_T2F[numberOfVertices];
            }

            if (item.GeometryPacket.Indicies.Length < numberOfIndicies)
            {
                item.GeometryPacket.Indicies = new int[numberOfIndicies];
            }

            item.GeometryPacket.NumberOfVertices = numberOfVertices;
            item.GeometryPacket.NumberOfIndicies = numberOfIndicies;

            batchItemList.Add(item);

            return(item);
        }
Beispiel #9
0
 public void AddLineVertex(CCV3F_C4B lineVertex)
 {
     lineVertices.Add(lineVertex);
 }
Beispiel #10
0
 public void AddTriangleVertex(CCV3F_C4B triangleVertex)
 {
     triangleVertices.Add(triangleVertex);
 }
Beispiel #11
0
        protected void UpdateLabel()
        {
            SetString(labelInitialText, false);

            if (string.IsNullOrEmpty(labelText))
            {
                return;
            }

            if (labelDimensions.Width > 0)
            {
                // Step 1: Make multiline
                string str_whole        = labelText;
                int    stringLength     = str_whole.Length;
                var    multiline_string = new StringBuilder(stringLength);
                var    last_word        = new StringBuilder(stringLength);

                int   line = 1, i = 0;
                bool  start_line = false, start_word = false;
                float startOfLine = -1, startOfWord = -1;
                int   skip = 0;

                CCRawList <CCNode> children = Children;
                for (int j = 0; j < children.Count; j++)
                {
                    CCSprite characterSprite;
                    int      justSkipped = 0;

                    while ((characterSprite = (CCSprite)this[(j + skip + justSkipped)]) == null)
                    {
                        justSkipped++;
                    }

                    skip += justSkipped;

                    if (!characterSprite.Visible)
                    {
                        continue;
                    }

                    if (i >= stringLength)
                    {
                        break;
                    }

                    char character = str_whole[i];

                    if (!start_word)
                    {
                        startOfWord = GetLetterPosXLeft(characterSprite);
                        start_word  = true;
                    }
                    if (!start_line)
                    {
                        startOfLine = startOfWord;
                        start_line  = true;
                    }

                    // Newline.
                    if (character == '\n')
                    {
                        int len = last_word.Length;
                        while (len > 0 && Char.IsWhiteSpace(last_word[len - 1]))
                        {
                            len--;
                            last_word.Remove(len, 1);
                        }

                        multiline_string.Append(last_word);
                        multiline_string.Append('\n');

                        last_word.Clear();

                        start_word  = false;
                        start_line  = false;
                        startOfWord = -1;
                        startOfLine = -1;
                        i          += justSkipped;
                        line++;

                        if (i >= stringLength)
                        {
                            break;
                        }

                        character = str_whole[i];

                        if (startOfWord == 0)
                        {
                            startOfWord = GetLetterPosXLeft(characterSprite);
                            start_word  = true;
                        }
                        if (startOfLine == 0)
                        {
                            startOfLine = startOfWord;
                            start_line  = true;
                        }
                    }

                    // Whitespace.
                    if (Char.IsWhiteSpace(character))
                    {
                        last_word.Append(character);
                        multiline_string.Append(last_word);
                        last_word.Clear();
                        start_word  = false;
                        startOfWord = -1;
                        i++;
                        continue;
                    }

                    // Out of bounds.
                    if (GetLetterPosXRight(characterSprite) - startOfLine > labelDimensions.Width)
                    {
                        if (!lineBreakWithoutSpaces)
                        {
                            last_word.Append(character);

                            int len = multiline_string.Length;
                            while (len > 0 && Char.IsWhiteSpace(multiline_string[len - 1]))
                            {
                                len--;
                                multiline_string.Remove(len, 1);
                            }

                            if (multiline_string.Length > 0)
                            {
                                multiline_string.Append('\n');
                            }

                            line++;
                            start_line  = false;
                            startOfLine = -1;
                            i++;
                        }
                        else
                        {
                            int len = last_word.Length;
                            while (len > 0 && Char.IsWhiteSpace(last_word[len - 1]))
                            {
                                len--;
                                last_word.Remove(len, 1);
                            }

                            multiline_string.Append(last_word);
                            multiline_string.Append('\n');

                            last_word.Clear();

                            start_word  = false;
                            start_line  = false;
                            startOfWord = -1;
                            startOfLine = -1;
                            line++;

                            if (i >= stringLength)
                            {
                                break;
                            }

                            if (startOfWord == 0)
                            {
                                startOfWord = GetLetterPosXLeft(characterSprite);
                                start_word  = true;
                            }
                            if (startOfLine == 0)
                            {
                                startOfLine = startOfWord;
                                start_line  = true;
                            }

                            j--;
                        }

                        continue;
                    }
                    else
                    {
                        // Character is normal.
                        last_word.Append(character);
                        i++;
                        continue;
                    }
                }

                multiline_string.Append(last_word);

                SetString(multiline_string.ToString(), false);
            }

            // Step 2: Make alignment
            if (horzAlignment != CCTextAlignment.Left)
            {
                int i = 0;

                int lineNumber = 0;
                int str_len    = labelText.Length;
                var last_line  = new CCRawList <char>();
                // If label dim is 0, then we need to use the content size width instead
                float maxLabelWidth = labelDimensions.Width > 0 ? labelDimensions.Width : ContentSize.Width;
                for (int ctr = 0; ctr <= str_len; ++ctr)
                {
                    if (ctr == str_len || labelText[ctr] == '\n')
                    {
                        float lineWidth   = 0.0f;
                        int   line_length = last_line.Count;
                        // if last line is empty we must just increase lineNumber and work with next line
                        if (line_length == 0)
                        {
                            lineNumber++;
                            continue;
                        }
                        int index = i + line_length - 1 + lineNumber;
                        if (index < 0)
                        {
                            continue;
                        }

                        var lastChar = (CCSprite)this[index];
                        if (lastChar == null)
                        {
                            continue;
                        }

                        lineWidth = lastChar.Position.X + lastChar.ContentSize.Width;

                        var shift = maxLabelWidth - lineWidth;
                        if (horzAlignment == CCTextAlignment.Center)
                        {
                            shift /= 2;
                        }

                        for (int j = 0; j < line_length; j++)
                        {
                            index = i + j + lineNumber;
                            if (index < 0)
                            {
                                continue;
                            }

                            var characterSprite = this[index];
                            characterSprite.PositionX += shift;
                        }

                        i += line_length;
                        lineNumber++;

                        last_line.Clear();
                        continue;
                    }

                    last_line.Add(labelText[ctr]);
                }
            }

            if (vertAlignment != CCVerticalTextAlignment.Bottom && labelDimensions.Height > 0)
            {
                int lineNumber = 1;
                int str_len    = labelText.Length;
                for (int ctr = 0; ctr < str_len; ++ctr)
                {
                    if (labelText[ctr] == '\n')
                    {
                        lineNumber++;
                    }
                }

                float yOffset = labelDimensions.Height - FontConfiguration.CommonHeight * lineNumber;

                if (vertAlignment == CCVerticalTextAlignment.Center)
                {
                    yOffset /= 2f;
                }

                for (int i = 0; i < str_len; i++)
                {
                    var characterSprite = this[i] as CCSprite;
                    if (characterSprite != null && characterSprite.Visible)
                    {
                        characterSprite.PositionY += yOffset;
                    }
                }
            }
        }
Beispiel #12
0
 public void AddLineVertex(CCV3F_C4B lineVertex)
 {
     lineVertices.Add(lineVertex);
     dirty = true;
 }
Beispiel #13
0
        private CCBMFontConfiguration InitializeFont(string fontName, float fontSize, string charset)
        {
            if (m_pData == null)
            {
                InitializeTTFAtlas(1024, 1024);
            }

            if (String.IsNullOrEmpty(charset))
            {
                charset = " ";
            }

            var chars = new CCRawList <char>();

            var fontKey = GetFontKey(fontName, fontSize);

            CCBMFontConfiguration fontConfig;

            if (!fontConfigurations.TryGetValue(fontKey, out fontConfig))
            {
                fontConfig = new CCBMFontConfiguration();
                fontConfigurations.Add(fontKey, fontConfig);
            }

            for (int i = 0; i < charset.Length; i++)
            {
                var ch = charset[i];
                if (!fontConfig.Glyphs.ContainsKey(ch) && chars.IndexOf(ch) == -1)
                {
                    chars.Add(ch);
                }
            }

            if (chars.Count == 0)
            {
                return(fontConfig);
            }

            CreateFont(fontName, fontSize, chars);

            fontConfig.CommonHeight = (int)Math.Ceiling(GetFontHeight());

            int[] data = null;

            for (int i = 0; i < chars.Count; i++)
            {
                var s = chars[i].ToString();

                var charSize = GetMeasureString(s);

                int w = (int)Math.Ceiling(charSize.Width + 2);
                int h = (int)Math.Ceiling(charSize.Height + 2);

                if (data == null || data.Length < (w * h))
                {
                    data = new int[w * h];
                }

                unsafe
                {
                    int   stride;
                    byte *pBase = GetBitmapData(s, out stride);

                    int minX = w;
                    int maxX = 0;
                    int minY = h;
                    int maxY = 0;

                    for (int y = 0; y < h; y++)
                    {
                        var row = (int *)(pBase + y * stride);

                        for (int x = 0; x < w; x++)
                        {
                            if (row[x] != 0)
                            {
                                minX = Math.Min(minX, x);
                                maxX = Math.Max(maxX, x);
                                minY = Math.Min(minY, y);
                                maxY = Math.Max(maxY, y);
                            }
                        }
                    }

                    w = Math.Max(maxX - minX + 1, 1);
                    h = Math.Max(maxY - minY + 1, 1);

                    //maxX = minX + w;
                    //maxY = minY + h;

                    int index = 0;
                    for (int y = minY; y <= maxY; y++)
                    {
                        var row = (int *)(pBase + y * stride);
                        for (int x = minX; x <= maxX; x++)
                        {
                            data[index] = row[x];
                            index++;
                        }
                    }

                    var region = AllocateRegion(w, h);

                    if (region.x >= 0)
                    {
                        SetRegionData(region, data, w);

                        var info = GetKerningInfo(chars[i]);

                        var fontDef = new CCBMFontConfiguration.CCBMGlyphDef()
                        {
                            Character = chars[i],
                            Subrect   = new CCRect(region.x, region.y, region.width, region.height),
                            XOffset   = minX, // + (int)Math.Ceiling(info.A),
                            YOffset   = minY,
                            XAdvance  = (int)Math.Ceiling(info.A + info.B + info.C)
                        };

                        fontConfig.CharacterSet.Add(chars[i]);
                        fontConfig.Glyphs.Add(chars[i], fontDef);
                    }
                    else
                    {
                        CCLog.Log("Texture atlas is full");
                    }
                }
            }

            isTextureDirty = true;

            return(fontConfig);
        }