RangeFormat.columnWidth и RangeFormat.autofitColumns () для API Officejs не работает

У меня проблема с columnWidth, который на самом деле не устанавливается и не отображается в Excel 2016. Ниже находится моя функция Excel.run:

        _columns = columns;
        var headers = [];
        var numCols = _columns.length;
        var letter = columnToLetter(numCols); //for perspective, this becomes "P"
        for (var i = 0; i < numCols; i++) {
            var header = [];
            header.push(_columns[i].header);
            headers.push(header); //basically an array of arrays, where each entry is ["some string"]
        }

        var ranges = [];
        Office.context.document.bindings.addFromNamedItemAsync(['Sheet1!A', letter].join(':'), 'table', { id: 'table' });

        Excel.run(function (context) {

            var sheet = context.workbook.worksheets.getItem("Sheet1");
            for (var i = 0; i < numCols; i++) {


                var range = sheet.getCell(0, i);
                range.load(['values', 'text', 'format/columnWidth']);
                ranges.push(range);

            }

            return context.sync().then(function () {

                for (var i = 0; i < numCols; i++) {
                    ranges[i].values = [headers[i]]; //now each range, which is essentially one cell, has one value in values. values = [["some string"]]
                    headerFormatFn(ranges[i]);
                    context.sync();
                }



            })
            .catch(function (err) { console.error(err); })
        });

и фактическое форматирование происходит в headerFormatFn (range [i]):

    function headerFormatFn(cell) {


        cell.format.font.bold = true;
        cell.format.borders.getItem(1).style = 'Continuous';
        cell.format.columnWidth = 80;

    }

Я проверил поддержку ExcelApi в своем Excel 2016 и знаю, что autofitColumns () не поддерживается, поэтому я понимаю, почему эта функция не работает. Для этого мне нужно обновить Excel 2016. Однако columnWidth - это свойство, которое поддерживается в ExcelApi 1.1, и поэтому оно поддерживается в моей версии Excel 2016.

Это странно, потому что format.font.bold и format.borders прекрасно работают. Похоже, что просто установка columnWidth не работает. См. Ниже вид полученного рабочего листа:

Итоговая таблица Excel 2016

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

------- ОБНОВЛЕНИЕ 1 -------

В ответ на ответ @Michael я внес следующие изменения:

Я изменил свой Excel.run на:

        Excel.run(function (context) {

            var sheet = context.workbook.worksheets.getItem("Sheet1");
            for (var i = 0; i < numCols; i++) {


                var range = sheet.getCell(0, i);
                range.load(['values', 'text', 'format/*']);
                ranges.push(range);

            }
            for (var i = 0; i < numCols; i++) {

                ranges[i].values = [headers[i]];
                headerFormatFn(ranges[i]);
            }
            return context.sync()
            .catch(function (err) { console.error(err); })
        });

и сейчас я использую border.getItemAt(0).style = 'Continuous':

        try {
            console.log("1");
            cell.format.font.bold = true;
            console.log("2");
            cell.format.borders.getItemAt(0).style = 'Continuous';
            console.log("3");
            cell.format.columnWidth = 80;
        }
        catch(error)
        {
            console.log(error);
        }

Журналы 1, 2 и 3 показывают, что цикл завершается, а затем выдает OfficeExtensionError InvalidArgument после цикла при вызове context.sync ().


person Joshua Landi    schedule 25.10.2016    source источник


Ответы (1)


Если бы мне пришлось угадывать, я думаю, что это строка cell.format.borders.getItem(1).style, которая вызывает проблему. Я не думаю, что вы можете сделать getItem(1), поскольку 1 не является допустимым ключом. Вместо этого вам нужно что-то вроде InsideHorizontal, например:

range.format.borders.getItem('InsideHorizontal').style = 'Continuous';

Когда что-то в пакете выходит из строя, дальнейшие изменения в очереди не выполняются, поэтому строка columnWidth не запускается.

При этом я думаю, что настоящая проблема с кодом заключается в том, что вы молча проглатываете ошибки, а также «нарушаете цепочку обещаний». Код нарушения:

            for (var i = 0; i < numCols; i++) {
                ...
                context.sync();
            }

С этим две проблемы:

  1. Вы делаете context.sync() в каждом цикле for. Вы почти наверняка не собираетесь этого делать (и это не удастся после того, как у вас будет ~ 50 столбцов, поскольку Excel может обрабатывать только X многих параллельных запросов). Вам нужно выполнить sync только один раз под циклом for.

  2. Вы не делаете «возврат» context.sync(). Это означает, что для всех намерений и целей Excel.run больше не ожидает в context.sync, а вместо этого завершает то, что делает, и движется дальше. context.sync() в этот момент становится отдельным рабочим потоком, который порождается, но не отслеживается родителем. Это означает, что catch на родительском элементе не может уловить какие-либо проблемы, возникающие во время этого дочернего sync.

Я занимаюсь созданием сайта / книги, чтобы раскрыть некоторые тайны Office.js и его внутренней работы. Я могу опубликовать здесь, когда у меня будет тема, готовая к просмотру (в частности, у меня есть тема «не нарушать цепочку обещаний»).

person Michael Zlatkovsky - Microsoft    schedule 25.10.2016
comment
Я добавил в свой вопрос изменения, предложенные в вашем ответе, но все еще получаю проблемы. См. ОБНОВЛЕНИЕ 1. Теперь я получаю разные ошибки, но столбцы по-прежнему не меняют размер. - person Joshua Landi; 25.10.2016
comment
Также важно то, что ошибка, которую я получаю сейчас, - это та, которую я уже получал, и поэтому я добавил context.sync () внутри цикла, потому что он таким образом заполнил все мои ячейки. Этот код никоим образом не доработан, я просто пытался найти способ заставить столбцы отображаться и изменять размер. - person Joshua Landi; 25.10.2016
comment
@JoshuaLandi, что-то в вашем обновленном коде не так: range.load(['values', 'text', 'format/*']); загружается, но не используется. Есть ли синхронизация, которую вы хотите где-то посреди всего этого? - person Michael Zlatkovsky - Microsoft; 26.10.2016
comment
@JoshuaLandi, я настоятельно рекомендую вам проверить свойство debugInfo объекта ошибки и посмотреть, на какое место он указывает. Это может оказаться большим подспорьем при диагностике вызова, вызывающего ошибку. - person Michael Zlatkovsky - Microsoft; 26.10.2016
comment
У вас также могут быть отдельные проблемы с Office.context.document.bindings.addFromNamedItemAsync, как вы его называете, но затем позволяете ему работать как есть, независимо от вашего другого блока кода (это предназначено?) - person Michael Zlatkovsky - Microsoft; 26.10.2016
comment
Итак, я в основном работаю с чужим кодом, который, казалось бы, был более знаком с OfficeJS, поэтому я оставил некоторый код и принял его как правильный. Но теперь, когда вы указали на это, я изменил способ форматирования, используя привязки и обратные вызовы. Однако это привело к другой проблеме, которую я опубликовал отдельно, поскольку это новая проблема. ссылка - person Joshua Landi; 27.10.2016