Пример #1
0
        private void createChildControlsAndWireUpEvents()
        {
            captionTable          = TableOps.CreateUnderlyingTable();
            captionTable.CssClass = "ewfStandardDynamicTableCaption";
            captionTable.Visible  = false;
            var row = new TableRow();

            var captionCell = new TableCell();

            captionCell.Controls.Add(captionStack = ControlStack.Create(false));
            row.Cells.Add(captionCell);

            var actionLinksCell = new TableCell {
                CssClass = "ewfAddItemLink"
            };

            actionLinksCell.Controls.Add(actionLinkStack = ControlStack.Create(false));
            row.Cells.Add(actionLinksCell);

            captionTable.Rows.Add(row);
            Controls.Add(captionTable);

            table = TableOps.CreateUnderlyingTable();
            Controls.Add(table);

            PreRender += ewfTable_PreRender;

            dataModifications = FormState.Current.DataModifications;
        }
        void ControlTreeDataLoader.LoadData()
        {
            if (dateModificationMethod == null)
            {
                throw new ApplicationException("In order to place this calendar on a page, you must call SetParameters before the end of LoadData.");
            }
            buildNavigationBox();

            // Begin drawing calendar
            var table = TableOps.CreateUnderlyingTable();

            table.Attributes["class"] = "ewfMonthView ewfMonthViewCalendar";
            base.Controls.Add(table);

            var headerRow = new TableRow();

            foreach (var day in Enum.GetValues(typeof(DayOfWeek)))
            {
                headerRow.Cells.Add(new TableCell {
                    Text = day.ToString(), CssClass = "commonHeader ewfDaysOfWeekHeader"
                });
            }
            table.Rows.Add(headerRow);

            var localDate      = IsTwoWeekCalendar ? date.WeekBeginDate() : new DateTime(date.Year, date.Month, 1).WeekBeginDate();
            var endDrawingDate = IsTwoWeekCalendar
                                                     ? localDate.AddDays(13)
                                                     : new DateTime(date.Year, date.Month, 1).AddDays(DateTime.DaysInMonth(date.Year, date.Month) - 1);

            do
            {
                var row = new TableRow();
                foreach (DayOfWeek dayOfWeek in Enum.GetValues(typeof(DayOfWeek)))
                {
                    var cell = new TableCell {
                        Text = " "
                    };
                    if (IsTwoWeekCalendar || localDate.Date.Month.CompareTo(date.Date.Month) == 0)
                    {
                        if (daysOfMonthToCells.ContainsKey(localDate))
                        {
                            cell = daysOfMonthToCells[localDate];
                        }

                        if (daysOfMonthToolTips.ContainsKey(localDate))
                        {
                            new ToolTip(daysOfMonthToolTips[localDate].Content, cell);
                        }
                    }
                    cell.Attributes.Add("class", localDate.CompareTo(DateTime.Now.Date) == 0 ? "ewfToday" : localDate.Month == date.Month ? "ewfDay" : "ewfDaySpacer");
                    cell.Controls.AddAt(0, new Paragraph(localDate.Day.ToString().GetLiteralControl())
                    {
                        CssClass = "dayLabel"
                    });
                    row.Cells.Add(cell);
                    localDate = localDate.AddDays(1);
                }
                table.Rows.Add(row);
            }while(localDate.CompareTo(endDrawingDate) <= 0);
        }
        /// <summary>
        /// Creates a new instance of a Control Line with the given controls.
        /// </summary>
        public ControlLine(params Control[] controls)
        {
            var table = TableOps.CreateUnderlyingTable();

            table.Rows.Add(row = new TableRow());
            base.Controls.Add(table);
            AddControls(controls);
            VerticalAlignment = TableCellVerticalAlignment.NotSpecified;
        }
Пример #4
0
        private void ewfTable_PreRender(object sender, EventArgs e)
        {
            // NOTE: This should all move to ControlTreeDataLoader.LoadData, but it can't right now because so many pages add table rows from PreRender.
            TableOps.AlternateRowColors(table, rowSetups);

            // NOTE: We should be able to get rid of this row hiding when we port everything over to use AddAllDataToTable.
            var dataRowIndex = 0;

            for (var rowIndex = 0; rowIndex < rowSetups.Count; rowIndex++)
            {
                table.Rows[rowIndex].Visible = dataRowIndex++ < CurrentDataRowLimit;
            }
        }
Пример #5
0
        void ControlTreeDataLoader.LoadData()
        {
            if (hideIfEmpty && itemGroups.All(itemGroup => !itemGroup.Items.Any()))
            {
                Visible = false;
                return;
            }

            EwfTable.SetUpTableAndCaption(this, style, classes, caption, subCaption);

            var itemSetupLists = new[] { headItems }.Concat(itemGroups.Select(i => i.Items)).Select(i => i.Select(j => j.Setup.FieldOrItemSetup));
            var allItemSetups     = itemSetupLists.SelectMany(i => i).ToImmutableArray();
            var columnWidthFactor = EwfTable.GetColumnWidthFactor(allItemSetups);

            foreach (var itemSetups in itemSetupLists.Where(i => i.Any()))
            {
                Controls.Add(
                    new WebControl(HtmlTextWriterTag.Colgroup).AddControlsReturnThis(itemSetups.Select(i => EwfTable.GetColControl(i, columnWidthFactor))));
            }

            var fields = EwfTable.GetFields(specifiedFields, headItems, itemGroups.SelectMany(i => i.Items));
            var cellPlaceholderListsForItems = TableOps.BuildCellPlaceholderListsForItems(
                headItems.Concat(itemGroups.SelectMany(i => i.Items)).ToList(),
                fields.Count);

            // Pivot the cell placeholders from column primary into row primary format.
            var cellPlaceholderListsForRows =
                Enumerable.Range(0, fields.Count)
                .Select(field => Enumerable.Range(0, allItemSetups.Length).Select(item => cellPlaceholderListsForItems[item][field]).ToList())
                .ToList();

            var headRows = TableOps.BuildRows(
                cellPlaceholderListsForRows.Take(firstDataFieldIndex).ToList(),
                fields.Select(i => i.FieldOrItemSetup).ToImmutableArray(),
                null,
                allItemSetups,
                allItemSetups.Length,
                true);
            var bodyRows = TableOps.BuildRows(
                cellPlaceholderListsForRows.Skip(firstDataFieldIndex).ToList(),
                fields.Select(i => i.FieldOrItemSetup).ToImmutableArray(),
                false,
                allItemSetups,
                headItems.Count,
                true);

            // We can't easily put the head fields in thead because we don't have a way of verifying that cells don't cross between head and data fields.
            Controls.Add(new WebControl(HtmlTextWriterTag.Tbody).AddControlsReturnThis(headRows.Concat(bodyRows)));

            EwfTable.AssertAtLeastOneCellPerField(fields, cellPlaceholderListsForItems);
        }
Пример #6
0
        private IEnumerable <Control> buildRows(
            IReadOnlyCollection <EwfTableItem> items, IReadOnlyCollection <EwfTableField> fields, bool?useContrastForFirstRow, bool useHeadCells,
            Func <EwfTableCell> itemActionCheckBoxCellGetter, Func <EwfTableCell> itemReorderingCellGetter, List <EwfTableItem> allVisibleItems)
        {
            // Assert that the cells in the list of items are valid and store a data structure for below.
            var cellPlaceholderListsForRows = TableOps.BuildCellPlaceholderListsForItems(items, fields.Count);

            // NOTE: Be sure to take check box and reordering columns into account.
            var rows = TableOps.BuildRows(
                cellPlaceholderListsForRows,
                items.Select(i => i.Setup.FieldOrItemSetup).ToImmutableArray(),
                useContrastForFirstRow,
                fields.Select(i => i.FieldOrItemSetup).ToImmutableArray(),
                useHeadCells ? fields.Count : 0,
                false);

            allVisibleItems.AddRange(items);
            return(rows);
        }
Пример #7
0
        void ControlTreeDataLoader.LoadData()
        {
            using (MiniProfiler.Current.Step("EWF - Load table data")) {
                FormState.ExecuteWithDataModificationsAndDefaultAction(
                    dataModifications,
                    () => {
                    if (hideIfEmpty && itemGroups.All(itemGroup => !itemGroup.Items.Any()))
                    {
                        Visible = false;
                        return;
                    }

                    SetUpTableAndCaption(this, style, classes, caption, subCaption);

                    var visibleItemGroupsAndItems = new List <Tuple <EwfTableItemGroup, IReadOnlyCollection <EwfTableItem> > >();
                    foreach (var itemGroup in itemGroups)
                    {
                        var visibleItems = itemGroup.Items.Take(CurrentItemLimit - visibleItemGroupsAndItems.Sum(i => i.Item2.Count)).Select(i => i());
                        visibleItemGroupsAndItems.Add(Tuple.Create <EwfTableItemGroup, IReadOnlyCollection <EwfTableItem> >(itemGroup, visibleItems.ToImmutableArray()));
                        if (visibleItemGroupsAndItems.Sum(i => i.Item2.Count) == CurrentItemLimit)
                        {
                            break;
                        }
                    }

                    var fields = GetFields(specifiedFields, headItems.AsReadOnly(), visibleItemGroupsAndItems.SelectMany(i => i.Item2));
                    if (!fields.Any())
                    {
                        fields = new EwfTableField().ToCollection();
                    }

                    addColumnSpecifications(fields);

                    var allVisibleItems = new List <EwfTableItem>();

                    var itemLimitingUpdateRegionSet = new UpdateRegionSet();
                    var headRows =
                        buildRows(
                            getItemLimitingAndGeneralActionsItem(fields.Count, itemLimitingUpdateRegionSet).Concat(getItemActionsItem(fields.Count)).ToList(),
                            Enumerable.Repeat(new EwfTableField(), fields.Count).ToArray(),
                            null,
                            false,
                            null,
                            null,
                            allVisibleItems).Concat(buildRows(headItems, fields, null, true, null, null, allVisibleItems)).ToArray();
                    if (headRows.Any())
                    {
                        Controls.Add(new WebControl(HtmlTextWriterTag.Thead).AddControlsReturnThis(headRows));
                    }

                    var bodyRowGroupsAndRows = new List <Tuple <WebControl, ImmutableArray <Control> > >();
                    var updateRegionSetListsAndStaticRowGroupCounts = new List <Tuple <IReadOnlyCollection <UpdateRegionSet>, int> >();
                    for (var visibleGroupIndex = 0; visibleGroupIndex < visibleItemGroupsAndItems.Count; visibleGroupIndex += 1)
                    {
                        var groupAndItems          = visibleItemGroupsAndItems[visibleGroupIndex];
                        var useContrastForFirstRow = visibleItemGroupsAndItems.Where((group, i) => i < visibleGroupIndex).Sum(i => i.Item2.Count) % 2 == 1;
                        var groupBodyRows          = buildRows(groupAndItems.Item2, fields, useContrastForFirstRow, false, null, null, allVisibleItems).ToImmutableArray();
                        var rowGroup =
                            new WebControl(HtmlTextWriterTag.Tbody).AddControlsReturnThis(
                                buildRows(
                                    groupAndItems.Item1.GetHeadItems(fields.Count),
                                    Enumerable.Repeat(new EwfTableField(), fields.Count).ToArray(),
                                    null,
                                    true,
                                    null,
                                    null,
                                    allVisibleItems).Concat(new NamingPlaceholder(groupBodyRows).ToCollection()));
                        bodyRowGroupsAndRows.Add(Tuple.Create(rowGroup, groupBodyRows));

                        var cachedVisibleGroupIndex = visibleGroupIndex;
                        EwfPage.Instance.AddUpdateRegionLinker(
                            new LegacyUpdateRegionLinker(
                                rowGroup,
                                "tail",
                                from region in groupAndItems.Item1.RemainingData.Value.TailUpdateRegions
                                let staticRowCount = itemGroups[cachedVisibleGroupIndex].Items.Count - region.UpdatingItemCount
                                                     select new LegacyPreModificationUpdateRegion(region.Sets, () => groupBodyRows.Skip(staticRowCount), staticRowCount.ToString),
                                arg => groupBodyRows.Skip(int.Parse(arg))));

                        // If item limiting is enabled, include all subsequent item groups in tail update regions since any number of items could be appended.
                        if (defaultItemLimit != DataRowLimit.Unlimited)
                        {
                            updateRegionSetListsAndStaticRowGroupCounts.Add(
                                Tuple.Create <IReadOnlyCollection <UpdateRegionSet>, int>(
                                    groupAndItems.Item1.RemainingData.Value.TailUpdateRegions.SelectMany(i => i.Sets).ToImmutableArray(),
                                    visibleGroupIndex + 1));
                        }
                    }
                    Controls.Add(new NamingPlaceholder(bodyRowGroupsAndRows.Select(i => i.Item1)));

                    if (defaultItemLimit != DataRowLimit.Unlimited)
                    {
                        var oldItemLimit   = CurrentItemLimit;
                        var lowerItemLimit = new Lazy <int>(() => Math.Min(oldItemLimit, CurrentItemLimit));

                        var itemLimitingTailUpdateRegionControlGetter = new Func <int, IEnumerable <Control> >(
                            staticItemCount => {
                            var rowCount = 0;
                            for (var groupIndex = 0; groupIndex < bodyRowGroupsAndRows.Count; groupIndex += 1)
                            {
                                var rows  = bodyRowGroupsAndRows[groupIndex].Item2;
                                rowCount += rows.Length;
                                if (rowCount < staticItemCount)
                                {
                                    continue;
                                }
                                return(rows.Skip(rows.Length - (rowCount - staticItemCount)).Concat(bodyRowGroupsAndRows.Skip(groupIndex + 1).Select(i => i.Item1)));
                            }
                            return(ImmutableArray <Control> .Empty);
                        });

                        EwfPage.Instance.AddUpdateRegionLinker(
                            new LegacyUpdateRegionLinker(
                                this,
                                "itemLimitingTail",
                                new LegacyPreModificationUpdateRegion(
                                    itemLimitingUpdateRegionSet.ToCollection(),
                                    () => itemLimitingTailUpdateRegionControlGetter(lowerItemLimit.Value),
                                    () => lowerItemLimit.Value.ToString()).ToCollection(),
                                arg => itemLimitingTailUpdateRegionControlGetter(int.Parse(arg))));
                    }

                    EwfPage.Instance.AddUpdateRegionLinker(
                        new LegacyUpdateRegionLinker(
                            this,
                            "tail",
                            from region in
                            tailUpdateRegions.Select(i => new { sets = i.Sets, staticRowGroupCount = itemGroups.Count - i.UpdatingItemCount })
                            .Concat(updateRegionSetListsAndStaticRowGroupCounts.Select(i => new { sets = i.Item1, staticRowGroupCount = i.Item2 }))
                            select
                            new LegacyPreModificationUpdateRegion(
                                region.sets,
                                () => bodyRowGroupsAndRows.Skip(region.staticRowGroupCount).Select(i => i.Item1),
                                region.staticRowGroupCount.ToString),
                            arg => bodyRowGroupsAndRows.Skip(int.Parse(arg)).Select(i => i.Item1)));

                    var itemCount            = itemGroups.Sum(i => i.Items.Count);
                    var itemLimitingRowGroup = new List <Control>();
                    if (CurrentItemLimit < itemCount)
                    {
                        var nextLimit          = EnumTools.GetValues <DataRowLimit>().First(i => i > (DataRowLimit)CurrentItemLimit);
                        var itemIncrementCount = Math.Min((int)nextLimit, itemCount) - CurrentItemLimit;
                        var button             = new PostBackButton(
                            new TextActionControlStyle("Show " + itemIncrementCount + " more item" + (itemIncrementCount != 1 ? "s" : "")),
                            usesSubmitBehavior: false,
                            postBack:
                            PostBack.CreateIntermediate(
                                itemLimitingUpdateRegionSet.ToCollection(),
                                id: PostBack.GetCompositeId(postBackIdBase, "showMore"),
                                firstModificationMethod: () => EwfPage.Instance.PageState.SetValue(this, itemLimitPageStateKey, (int)nextLimit)));
                        var item        = new EwfTableItem(button.ToCell(new TableCellSetup(fieldSpan: fields.Count)));
                        var useContrast = visibleItemGroupsAndItems.Sum(i => i.Item2.Count) % 2 == 1;
                        itemLimitingRowGroup.Add(
                            new WebControl(HtmlTextWriterTag.Tbody).AddControlsReturnThis(
                                buildRows(
                                    item.ToCollection().ToList(),
                                    Enumerable.Repeat(new EwfTableField(), fields.Count).ToArray(),
                                    useContrast,
                                    false,
                                    null,
                                    null,
                                    allVisibleItems)));
                    }
                    Controls.Add(
                        new NamingPlaceholder(
                            itemLimitingRowGroup,
                            updateRegionSets:
                            itemLimitingUpdateRegionSet.ToCollection()
                            .Concat(
                                itemGroups.SelectMany(i => i.RemainingData.Value.TailUpdateRegions).ToImmutableArray().Concat(tailUpdateRegions).SelectMany(i => i.Sets))));

                    // Assert that every visible item in the table has the same number of cells and store a data structure for below.
                    var cellPlaceholderListsForItems = TableOps.BuildCellPlaceholderListsForItems(allVisibleItems, fields.Count);

                    if (!disableEmptyFieldDetection)
                    {
                        AssertAtLeastOneCellPerField(fields, cellPlaceholderListsForItems);
                    }
                });
            }
        }
Пример #8
0
        /// <summary>
        /// Adds a row to this table.
        /// </summary>
        public void AddRow(RowSetup rowSetup, params EwfTableCell[] cells)
        {
            // If SetUpColumns was never called, implicitly set up the columns based on this first row.
            if (columnSetups == null)
            {
                columnSetups = cells.Select(c => new ColumnSetup()).ToList();
            }

            rowSetups.Add(rowSetup);
            if (!rowSetup.IsHeader)
            {
                dataRowCount++;
            }

            var defaultCsvLine = cells.Select(cell => (cell as CellPlaceholder).SimpleText).ToList();

            if (rowSetup.CsvLine == null)
            {
                rowSetup.CsvLine = defaultCsvLine;
            }

            // Verify that this row has the right number of cells.
            try {
                if (cells.Sum(c => c.Setup.FieldSpan) + previousRowColumnSpans.Sum(rcSpan => rcSpan.ColumnSpan) != columnSetups.Count)
                {
                    throw new ApplicationException("Row to be added has the wrong number of cells.");
                }

                // Despite that it would make no sense to do this and all latest browsers will draw tables incorrectly when this happens, I cannot find official documentation
                // saying that it is wrong. NOTE: This check isn't as good as the logic we are going to add to EwfTableItemRemainingData (to ensure that the item has at
                // least one cell) because it doesn't catch a case like two cells that each have a row span greater than one and together span all columns.
                if (cells.Any(c => c.Setup.ItemSpan > 1 && c.Setup.FieldSpan == columnSetups.Count))
                {
                    throw new ApplicationException("Cell may not take up all columns and span multiple rows.");
                }
            }
            catch (ApplicationException e) {
                if (!ConfigurationStatics.IsDevelopmentInstallation)
                {
                    TelemetryStatics.ReportError(e);
                }
                else
                {
                    throw;
                }
            }
            foreach (var rowColumnSpanPair in previousRowColumnSpans)
            {
                rowColumnSpanPair.RowSpan--;
            }

            previousRowColumnSpans =
                (previousRowColumnSpans.Where(rowSpan => rowSpan.RowSpan > 0)
                 .Concat(
                     cells.Where(c => c.Setup.ItemSpan != 1)
                     .Select(rowSpanCell => new RowColumnSpanPair {
                RowSpan = rowSpanCell.Setup.ItemSpan - 1, ColumnSpan = rowSpanCell.Setup.FieldSpan
            }))).ToList();

            var cellPlaceHolders = new List <CellPlaceholder>(cells);

            TableOps.DrawRow(table, rowSetup, cellPlaceHolders, columnSetups, false);
        }