it-roy-ru.com

Как автоматически изменять ширину столбца в AngularJS ui-grid

В AngularJS i-grid как я могу настроить сетку так, чтобы она могла автоматически регулировать ширину столбцов в соответствии с содержимым при рендеринге?

Я знаю, что есть учебник , показывающий функцию авторазмера, но она работает только при двойном щелчке по столбцу, я бы хотел, чтобы это происходило при инициализации сетки.

13
Tony

Я не думаю, что эта функция существует на данный момент. Директива uiGridColumnResizer регистрирует прослушиватели событий в dblclick, mousedown и mouseup. Событие dblclick в основном проходит через все визуализированные ячейки, вычисляет максимальную ширину и устанавливает его в качестве ширины столбца. Это будет проблемой производительности, если у вас будет много отображаемых строк. 

Я бы, вероятно, просто установил максимально возможную ширину на основе данных, которые будет иметь сетка. 

Или попробуйте повторить поведение в uiGridColumnResizer. 

 $Elm.on('dblclick', function(event, args) {
      event.stopPropagation();

      var col = uiGridResizeColumnsService.findTargetCol($scope.col, $scope.position, rtlMultiplier);

      // Don't resize if it's disabled on this column
      if (col.colDef.enableColumnResizing === false) {
        return;
      }

      // Go through the rendered rows and find out the max size for the data in this column
      var maxWidth = 0;
      var xDiff = 0;

      // Get the parent render container element
      var renderContainerElm = gridUtil.closestElm($Elm, '.ui-grid-render-container');

      // Get the cell contents so we measure correctly. For the header cell we have to account for the sort icon and the menu buttons, if present
      var cells = renderContainerElm.querySelectorAll('.' + uiGridConstants.COL_CLASS_PREFIX + col.uid + ' .ui-grid-cell-contents');
      Array.prototype.forEach.call(cells, function (cell) {
          // Get the cell width
          // gridUtil.logDebug('width', gridUtil.elementWidth(cell));

          // Account for the menu button if it exists
          var menuButton;
          if (angular.element(cell).parent().hasClass('ui-grid-header-cell')) {
            menuButton = angular.element(cell).parent()[0].querySelectorAll('.ui-grid-column-menu-button');
          }

          gridUtil.fakeElement(cell, {}, function(newElm) {
            // Make the element float since it's a div and can expand to fill its container
            var e = angular.element(newElm);
            e.attr('style', 'float: left');

            var width = gridUtil.elementWidth(e);

            if (menuButton) {
              var menuButtonWidth = gridUtil.elementWidth(menuButton);
              width = width + menuButtonWidth;
            }

            if (width > maxWidth) {
              maxWidth = width;
              xDiff = maxWidth - width;
            }
          });
        });

      // check we're not outside the allowable bounds for this column
      col.width = constrainWidth(col, maxWidth);

      // All other columns because fixed to their drawn width, if they aren't already
      resizeAroundColumn(col);

      buildColumnsAndRefresh(xDiff);

      uiGridResizeColumnsService.fireColumnSizeChanged(uiGridCtrl.grid, col.colDef, xDiff);
    });
4
Kathir

используйте звездочку в определении вашего столбца:

width:"*";
3
cramroop

Есть плагин, который делает это: ui-grid-auto-fit-columns

GitHub: https://github.com/Den-dp/ui-grid-auto-fit-columns

Пример: http://jsbin.com/tufazaw/edit?js,output

Использование:

<div ui-grid="gridOptions" ui-grid-auto-fit-columns></div>

angular.module('app', ['ui.grid', 'ui.grid.autoFitColumns'])
2
Leonel Thiesen

Итак, это сработало для меня, когда мне нужно было сжать все столбцы, кроме одного. Я перебираю все столбцы после завершения загрузки сетки и запускаю событие двойного щелчка на ресайзере. Не самая красивая, поэтому, если у кого-то есть лучшее решение, я буду очень рад его услышать!

function resizeColumn(uid) {
    // document.querySelector might not be supported; if you have jQuery
    // in your project, it might be wise to use that for selecting this
    // element instead
    var resizer = document.querySelector('.ui-grid-col' + uid + ' .ui-grid-column-resizer.right');
    angular.element(resizer).triggerHandler('dblclick');
}

var gridOptions = {
    ...
    onRegisterApi: function (gridApi) {
        // why $interval instead of $timeout? beats me, I'm not smart enough
        // to figure out why, but $timeout repeated infinitely for me
        $interval(function() {
            var columns = gridApi.grid.columns;
            for(var i = 0; i < columns.length; i++) {
                // your conditional here
                if(columns[i].field !== 'name') {
                    resizeColumn(columns[i].uid)
                }
            }
        }, 0, 1);
    }
}
1
SnailCoil

Использование width : "*", настроит все столбцы в доступном порте просмотра, что приведет к сжатию столбцов.

Задание minWidth: "somevalue" и width: "*" улучшает внешний вид вашей пользовательской сетки 

1
rtvalluri

вы можете использовать * как в свойстве width - это считается autoвы можете увидеть здесь

1
yanai edri

Лучшее решение, которое я могу придумать, это:

  1. установите ширину сетки на 100% 
  2. установите атрибут maxWidth: для columnDefs, размер которого вы не хотите увеличивать до небольшого числа
  3. пусть размер сетки сам

hTML:

ui-grid="gridOptions" class="myuigrid" ui-ui-grid-resize-columns ui-grid-ui-grid-auto-resize></div>

cSS:

.myuigrid {
   width: 100%;
 }

jS

            columnDefs: [
              { name: 'Id', maxWidth:80 },
              { name: 'Name', maxWidth: 280 },
              { name: 'LongName'},
            ],

Я знаю, что это не сработает в каждом случае, но в большинстве случаев большинство ваших столбцов более или менее фиксированы, и переменные, которые вы знаете заранее, позволяют изменять размер.

0
Rob Sedgwick

добавить следующее в gridoptions

                    init: function (gridCtrl, gridScope) {
                        gridScope.$on('ngGridEventData', function () {
                            $timeout(function () {
                                angular.forEach(gridScope.columns, function (col) {
                                    gridCtrl.resizeOnData(col);
                                });
                            });
                        });
                    }

Убедитесь, что у вас есть ширина любого случайного числа в каждом определении столбца

width: 100 

это хорошо.

0
lazell

Я не нашел никакой реализации для этого, так что это то, что я сделал 

  1. Перебрал первые 10 записей.

  2. Найден максимальный размер данных для каждого столбца.

  3. Затем на лету создал тег span и обернул его этими данными.

  4. Измеряется ширина тега, и это будет приблизительная ширина, необходимая для столбца (может потребоваться добавить более постоянную ширину из-за эффекта CSS и т.д.).

  5. Если первые 10 записей являются null, выполните тот же процесс, но на этот раз с заголовком столбца.

0
Python Boy

Я нашел некоторые проблемы с шириной решения. Мы должны использовать свойство 'cellClass' в объекте столбцов пользовательского интерфейса, чтобы включить этот класс. 

.ui-grid-cell-contents-auto {
     /* Old Solution */
    /*min-width: max-content !important;*/

    /* New Solution */
    display: grid;
    grid-auto-columns: max-content;

    /* IE Solution */
    display: -ms-grid;
    -ms-grid-columns: max-content;
}

тогда вы должны использовать свойство cellClass в объекте ui-grid columns для включения этого класса в вашей сетке (что-то вроде этого):

columns: [{ field: 'search_name', displayName: '', cellClass: 'ui-grid-cell-contents-auto'}]

Вы можете обратиться к подробному описанию ответа nekhaly's. https://github.com/angular-ui/ui-grid/issues/3913

0
level