public void JoinSelections() { if (selections.Count == 0) { return; } selectionsBuffer.Resize(selections.Count); for (int i = 0; i < selections.Count; i++) { Selection selection = selections[i]; selection.needRemove = false; selectionsBuffer.buffer[i] = selection; } Array.Sort(selectionsBuffer.buffer, 0, selectionsBuffer.count, selectionComparer); int count; count = selectionsBuffer.count; Selection current = selectionsBuffer.buffer[0]; for (int i = 1; i < count; i++) { int currentRight = current.Right; int iLeft = selectionsBuffer.buffer[i].Left; if (currentRight > iLeft || (current.Empty || selectionsBuffer.buffer[i].Empty) && currentRight >= iLeft) { selectionsBuffer.buffer[i].needRemove = true; int right = currentRight >= selectionsBuffer.buffer[i].Right ? currentRight : selectionsBuffer.buffer[i].Right; if (current.caret >= current.anchor) { current.caret = right; } else { current.anchor = right; } } else { current = selectionsBuffer.buffer[i]; } } selectionsBuffer.Clear(); for (int i = selections.Count; i-- > 0;) { if (selections[i].needRemove) { selections.RemoveAt(i); } } }
public void CalcCutOffs(int wwSizeX) { this.wwSizeX = wwSizeX; cutOffs.Clear(); int count = charsCount; if (count > 4) { int i; int left = GetFirstSpaceSize(out i); int pos = left; int lastSeparator = 0; int prevLastSeparator = 0; int lastPos = 0; char prev = '\0'; while (i < count) { char c = chars[i].c; if (!char.IsWhiteSpace(c) && (char.IsWhiteSpace(prev) || !char.IsLetterOrDigit(c))) { prevLastSeparator = lastSeparator; lastSeparator = i; lastPos = pos; } if (pos >= wwSizeX) { if (lastSeparator > prevLastSeparator) { i = lastSeparator; } else { if (left > 0 && cutOffs.count > 0) { int index = cutOffs.count - 1; CutOff prevCutOff = cutOffs.buffer[index]; cutOffs.buffer[index] = new CutOff(prevCutOff.iChar, 0, prevCutOff.sizeX); pos -= left; left = 0; prev = c; pos = c == '\t' ? ((pos + tabSize) / tabSize) * tabSize : pos + 1; ++i; continue; } else { lastSeparator = i; lastPos = pos; } } cutOffs.Add(new CutOff(lastSeparator, left, lastPos)); pos = left; prevLastSeparator = lastSeparator; prev = '\0'; } else { prev = c; pos = c == '\t' ? ((pos + tabSize) / tabSize) * tabSize : pos + 1; ++i; } } lastSublineSizeX = pos; } else { lastSublineSizeX = Size; } }
protected void InsertValuesRange(int index, T[] values) { if (index > this.valuesCount || index < 0) { throw new IndexOutOfRangeException("index=" + index + " is out of [0, " + this.valuesCount + "]"); } int valuesCount = values.Length; int i; if (this.valuesCount == 0) { AllocateBlocks(1); blocksCount = 1; blocks[0] = NewBlock(); i = 0; } else if (index == this.valuesCount) { i = blocksCount - 1; } else { i = GetBlockIndex(index); } TBlock target = blocks[i]; int j = index - target.offset; if (j == 0 && i > 0 && blockSize - blocks[i - 1].count >= valuesCount) { i--; target = blocks[i]; j = index - target.offset; } if (valuesCount <= blockSize - target.count) { Array.Copy(target.array, j, target.array, j + valuesCount, target.count - j); Array.Copy(values, 0, target.array, j, valuesCount); target.count += valuesCount; target.valid = 0; target.wwSizeX = 0; UpdateIndices(i); return; } blocksBuffer.Clear(); TBlock first; int firstJ; if (i > 0) { TBlock left = blocks[i - 1]; if (j <= blockSize - left.count) { int leftCount = left.count; first = left; firstJ = leftCount + j; Array.Copy(target.array, 0, left.array, leftCount, j); first.count += j; } else { int leftCount = left.count; first = NewBlock(); firstJ = j - (blockSize - leftCount); blocksBuffer.Add(first); Array.Copy(target.array, 0, left.array, leftCount, blockSize - leftCount); left.count = blockSize; left.valid = 0; left.wwSizeX = 0; Array.Copy(target.array, blockSize - leftCount, first.array, 0, j - (blockSize - leftCount)); first.count = j - (blockSize - leftCount); } first.valid = 0; first.wwSizeX = 0; } else { first = NewBlock(); firstJ = j; blocksBuffer.Add(first); Array.Copy(target.array, 0, first.array, 0, j); first.count = j; } int targetRightCount = target.count - j; if (first.count + valuesCount + targetRightCount <= blockSize) //!!!! NOT COVERED !!!!!! { // first: [--------|-values-|-targetRight-|---] Array.Copy(values, 0, first.array, first.count, valuesCount); first.count += valuesCount; Array.Copy(target.array, j, first.array, first.count, targetRightCount); first.count += targetRightCount; } else if (first.count + valuesCount <= blockSize) { // first: [--------|-values-|-targetRight-----] // last: [-targetRight-|---------------------] int targetRightCount0 = blockSize - (first.count + valuesCount); Array.Copy(values, 0, first.array, first.count, valuesCount); Array.Copy(target.array, j, first.array, first.count + valuesCount, targetRightCount0); TBlock last = NewBlock(); blocksBuffer.Add(last); Array.Copy(target.array, j + targetRightCount0, last.array, 0, targetRightCount - targetRightCount0); first.count = blockSize; last.count = targetRightCount - targetRightCount0; } else { int valuesFirstCount = blockSize - first.count; Array.Copy(values, 0, first.array, first.count, valuesFirstCount); first.count = blockSize; int n = (valuesCount - valuesFirstCount) / blockSize; int valuesLastCount = (valuesCount - valuesFirstCount) - n * blockSize; for (int ii = 0; ii < n; ii++) { TBlock block = NewBlock(); blocksBuffer.Add(block); Array.Copy(values, valuesFirstCount + ii * blockSize, block.array, 0, blockSize); block.count = blockSize; } if (valuesLastCount + targetRightCount > 0) { TBlock last = NewBlock(); blocksBuffer.Add(last); Array.Copy(values, valuesCount - valuesLastCount, last.array, 0, valuesLastCount); if (valuesLastCount + targetRightCount <= blockSize) { Array.Copy(target.array, j, last.array, valuesLastCount, targetRightCount); last.count = valuesLastCount + targetRightCount; } else { Array.Copy(target.array, j, last.array, valuesLastCount, blockSize - valuesLastCount); TBlock last2 = NewBlock(); blocksBuffer.Add(last2); Array.Copy(target.array, j + (blockSize - valuesLastCount), last2.array, 0, targetRightCount - (blockSize - valuesLastCount)); last.count = blockSize; last2.count = targetRightCount - (blockSize - valuesLastCount); } } } if (blocksBuffer.count == 0) //!!!! NOT COVERED !!!!!! { RemoveBlocks(i, i + 1); } else if (blocksBuffer.count == 1) { blocks[i] = blocksBuffer.buffer[0]; } else { int oldBlocksCount = blocksCount; AllocateBlocks(blocksCount - 1 + blocksBuffer.count); Array.Copy(blocks, i + 1, blocks, i + blocksBuffer.count, oldBlocksCount - i - 1); int blocksBufferCount = blocksBuffer.count; for (int ii = 0; ii < blocksBufferCount; ii++) { blocks[ii + i] = blocksBuffer.buffer[ii]; } } blocksBuffer.Clear(); UpdateIndices(i); }
protected override void OnPaint(PaintEventArgs e) { Graphics g = e.Graphics; int width = Width; int x = charWidth; int indent = charWidth; int yOffset = 3; g.FillRectangle(scheme.tabsBg.brush, 0, 0, width - charWidth, charHeight); leftIndent = charWidth; if (text != null) { Brush fg = scheme.tabsFg.brush; for (int j = 0; j < text.Length; j++) { g.DrawString(text[j] + "", font, fg, 10 - charWidth / 3 + j * charWidth, yOffset, stringFormat); } leftIndent += (charWidth + 1) * text.Length; } rects.Clear(); if (list != null) { for (int i = 0; i < list.Count; i++) { T value = list[i]; string tabText = stringOf(value); Rectangle rect = new Rectangle(x - indent, 0, tabText.Length * charWidth + indent * 2, charHeight); x += tabText.Length * charWidth + indent * 2; rects.Add(rect); } } string text2 = list != null && list.Selected != null && text2Of != null? text2Of(list.Selected) : text2 = this.text2; rightIndent = charHeight * 5 / 4 + (text2 != null ? text2.Length * charWidth : 0); if (x > width - leftIndent - rightIndent && list.Count > 1) { rightIndent += charHeight * 5 / 4; leftRect = new Rectangle(width - rightIndent, 0, charWidth * 3 / 2, charHeight); rightRect = new Rectangle(width - rightIndent + charWidth * 3 / 2, 0, charWidth * 3 / 2, charHeight); ScrollToSelectedIfNeed(); if (offsetIndex < 0) { offsetIndex = 0; } else if (offsetIndex > rects.count - 1) { offsetIndex = rects.count - 1; } if (offsetIndex > 0) { for (int i = offsetIndex; i-- > 0;) { if (rects.buffer[rects.count - 1].Right + GetOffsetX(i) > width - rightIndent - 1) { break; } offsetIndex = i; } } } else { leftRect = null; rightRect = null; offsetIndex = 0; } int selectedX0 = 0; int selectedX1 = 0; if (list != null) { int offsetX = GetOffsetX(offsetIndex); int selectedIndex = list.IndexOf(list.Selected); bool prevSelected = false; for (int i = Math.Max(0, offsetIndex - 1); i < list.Count; i++) { T value = list[i]; string tabText = stringOf(value); bool isCurrent = !buttonMode && object.Equals(list.Selected, value); Rectangle rect = rects.buffer[i]; rect.X += offsetX; if (rect.X > width) { break; } if (isCurrent) { tempPoints4[0] = new Point(rect.X + 1, rect.Y + 1); tempPoints4[1] = new Point(rect.X + rect.Width - rect.Height / 2, rect.Y + 1); tempPoints4[2] = new Point(rect.X + rect.Width + rect.Height / 2, rect.Y + rect.Height); tempPoints4[3] = new Point(rect.X + 1, rect.Y + rect.Height); g.FillPolygon(scheme.tabsSelectedBg.brush, tempPoints4); selectedX0 = rect.X; selectedX1 = rect.X + rect.Width; } if (!isCurrent) { if (buttonMode) { g.FillRectangle(scheme.buttonBgBrush, rect.X + 1, rect.Y + 2, rect.Width - 2, rect.Height - 4); } else if (i < selectedIndex) { g.FillRectangle(scheme.tabsUnselectedBg.brush, rect.X + 1, rect.Y + 1, rect.Width - 1, rect.Height - 2); } else { tempPoints4[0] = new Point(rect.X - rect.Height / 2 + 1, rect.Y + 1); tempPoints4[1] = new Point(rect.X + rect.Width - rect.Height / 2, rect.Y + 1); tempPoints4[2] = new Point(rect.X + rect.Width + rect.Height / 2 - 1, rect.Y + rect.Height - 1); tempPoints4[3] = new Point(rect.X + rect.Height / 2, rect.Y + rect.Height - 1); g.FillPolygon(scheme.tabsUnselectedBg.brush, tempPoints4); } } Brush currentFg = isCurrent ? scheme.tabsSelectedFg.brush : scheme.tabsUnselectedFg.brush; if (buttonMode) { currentFg = scheme.buttonFgBrush; } for (int j = 0; j < tabText.Length; j++) { int charX = rect.X - charWidth / 3 + j * charWidth + indent; if (charX > 0 && charX < width - rightIndent - charWidth * 2) { g.DrawString(tabText[j] + "", font, currentFg, charX, yOffset, stringFormat); } } rects.Add(rect); prevSelected = isCurrent; } } int fictiveIndent = rightIndent - charHeight / 4; { tempPoints5[0] = new Point(width - fictiveIndent - charHeight / 2, charHeight / 2); tempPoints5[1] = new Point(width - fictiveIndent, 0); tempPoints5[2] = new Point(width, 0); tempPoints5[3] = new Point(width, charHeight); tempPoints5[4] = new Point(width - fictiveIndent + (charHeight % 2), charHeight); g.FillPolygon(_selected ? scheme.tabsInfoBg.brush : scheme.tabsBg.brush, tempPoints5); Pen pen = _selected ? scheme.tabsBg.pen : scheme.tabsInfoBg.pen; g.DrawLine(pen, new Point(width - fictiveIndent, 0), new Point(width - fictiveIndent - charHeight / 2, charHeight / 2)); g.DrawLine(pen, new Point(width - fictiveIndent - charHeight / 2, charHeight / 2), new Point(width - fictiveIndent + (charHeight % 2), charHeight)); } int closeWidth = charHeight * 12 / 10; closeRect = new Rectangle(width - closeWidth, 0, closeWidth, charHeight); DrawCross(g); if (leftRect != null) { DrawArrow(g, true); } if (rightRect != null) { DrawArrow(g, false); } if (text2 != null) { Brush infoBrush = _selected ? scheme.tabsInfoFg.brush : scheme.tabsFg.brush; int left = width - text2.Length * charWidth - charHeight * 3 / 2; for (int j = 0; j < text2.Length; j++) { g.DrawString( text2[j] + "", font, infoBrush, left + charWidth * 2 / 3 + j * charWidth, yOffset - 2, stringFormat); } } base.OnPaint(e); }