Direct3D 10

Поделись знанием:
(перенаправлено с «DirectX 10»)
Перейти к: навигация, поиск

Direct3D 10 — набор API функций для взаимодействия с видеокартой; поддерживается аппаратно видеокартами класса NV GeForce 8x00, ATI Radeon 2x00 и выше. Direct3D 10 (D3D10) — компонент интерфейса программирования приложений (англ. API) DirectX 10, 10-я версия Direct3D, преемник Direct3D 9. Direct3D 10 обеспечивает функции для взаимодействия операционной системы и приложений с драйверами видеокарты. Эти функции привязаны к операционной системе в линейке Windows и доступны в Windows Vista и Windows 7 . Частично D3D10 работает на видеокартах уровня Direct3D 9.

Официальная финальная версия вышла 10 ноября 2006 года в составе Windows Vista.


Далее приведены ключевые особенности и отличия от Direct3D версии 9.





Возможности и особенности

Новая модель драйвера

В Windows Vista совершенно новая модель драйвера — WDDM (Windows Display Driver Model, ранее называемая LDDM — Longhorn Display Driver Model) — серьезное изменение в модели видеодрайвера со времен появления аппаратного ускорения. В XDDM (Windows XP Display Driver Model) каждый вызов DirectX добавлял указатель команды (токен) в буфер команд в независимом от видеокарты формате. Когда DX Runtime решал, что буфер достаточно заполнен, вызывалась функция драйвера (в режиме ядра), которая получала этот буфер. После этого драйвер разбирал этот буфер и передавал данные видеокарте. То есть никаких функций драйвера в пользовательском режиме не было. Развитие видеокарт и, как следствие, усложнение буфера команд привело к тому, что драйвер стал немыслимо большим и в случае любой ошибки провоцировал BSOD. Также в XDDM у операционной системы нет способов установления приоритета, управления видеопамятью, планирования вызовов DX, что затрудняет разделение видеокарты между несколькими процессами — причина «потери устройства».

В новой модели драйвера сделано разделение между пользовательской и работающей в режиме ядра частью драйвера. Все вызовы DX напрямую идут в пользовательский драйвер, который готовит сразу буфер с содержимым, зависящим от оборудования. Этот буфер передаёт данные в ядро операционной системы, откуда они идут на видеокарту. Таким образом вся тяжёлая работа выполняется в пользовательской части, а в ядре — только пересылка собранного буфера на видеокарту. Как итог, если пользовательский драйвер упадет, ничего страшного не случится — закроется конкретное приложение, но не произойдёт BSOD. Кроме того, теперь драйвер решает когда и сколько вызовов функций ядра делать. Также DX Runtime становится совсем тонкий — нет буферов команд, напрямую вызываются функции драйвера. Кроме этого между пользовательскими и ядерными частями есть планировщик заданий, который выбирает какие собранные буфера отправлять видеокарте (разделение GPU на много процессов).

Виртуализация видеопамяти

Теперь если не хватает видеопамяти, то ресурсы переносятся в системную (откуда могут быть отсвоплены). За счёт наличия у Windows Vista контроля выделения видеопамяти (ранее, у драйвера) можно распределять её более эффективно, чем POOL_MANAGED в XDDM. На данном этапе это работает на программном уровне — планировщик GPU перед передачей DMA-пакета карте загружает все нужные текстуры в видеопамять (умеет подгружать их заранее, пока GPU занят другим и свободна шина). Если приложение полноэкранное, все лишнее из видеопамяти будет перенесено в системную память по мере необходимости; если в оконном режиме, то происходит разделение памяти между текущими процессами. Если требуется гарантировать 100 % наличие ресурса в видеопамяти, то необходимо использовать полноэкранный режим и контроль над размером выделений.

Отсутствие ситуации «потери устройства» (Device Lost)

В предыдущих версиях по различным причинам мог происходить Device Lost, после чего требовалось загружать все ресурсы в видеопамять заново и производить восстановление объектов. С новой моделью драйвера этой проблемы больше не существует. Возможна ситуация Device Removed, которая означает, что видеокарта была физически удалена из системы или что видеодрайвер был обновлён. Ситуация встречается очень редко.

Убраны списки возможностей (D3D caps)

В DX10 гарантируется наличие всей функциональности, то есть если карта поддерживает DX10, то она обязана поддерживать последнюю версию шейдеров в полном объёме, поддерживать все форматы текстур, все возможные режимы фильтрации, шаблона (stencil) и всего остального. Более того, для DX10 написали спецификацию правил растеризации, то есть теперь картинка на разных видеокартах на одинаковом коде всегда должна быть одинаковой и совпадать с эталонным программным растеризатором. Если это не так, то это баг производителя видеокарты. В дальнейшем функциональность будет расширяться (пакет DX10.1, DX11 и т. д.).

Уменьшено время вызова функций DirectX

Уменьшено время вызова функций (в том числе DIP) на CPU. По данным презентаций Microsoft можно наблюдать 10x уменьшение времени. Это существенно, так как тяжёлая игра может проводить около 10+ миллисекунд в вызовах DX. Большую часть времени вызова ранее уходило на Runtime и Driver. теперь driver model фактически ничего не делает, а сразу предоставляет исполнение драйверу.

State Objects и Constant Buffers

Появились State Objects — объекты, которые можно предварительно собрать при создании и потом быстро устанавливать на видеокарте. Добавлены Constant Buffers, позволяющие более эффективно выставлять константы шейдеров.

Использование объектов-состояний

Все Set*State заменены на объекты-состояния (State Objects). Состояния разделены по нескольким группам:

  • Rasterizer State — fill mode, cull mode, depth bias, multisample, scissor и т. д.
  • Blend State — alpha blend, color write mask, blend op и т. д.
  • Depth State — depth func, stencil func и т. д.
  • SamplerState — tex filtering, clamping и т. д.

Состояния для каждой группы ставятся целиком, а не каждый по отдельности, как в D3D9. Для каждой группы можно создать State Object, которому при создании указывается полный набор состояний группы, и «установить» можно только его. Создание State Object — дорогая и медленная операция и должна вызываться редко. Мотивация этого нововведения — такой API позволяет драйверу сгенерировать набор команд видеокарте заранее (при создании State Object) и не генерировать его каждый раз во время рендера при вызовах Set*State.

Буфера и биндинг

Для основных типов данных (вершин, индексов, констант) введён единый буфер — ID3D10Buffer — набор байтов в памяти. Type safe обеспечивается за счёт указания при создании содержимого буфера. Для ресурсов введены отдельные объекты для привязки к конвейеру — resource views. То есть сначала создаем текстуру как объект в памяти, а потом её resource view как входные дынные для шейдера или как render target, и уже с этим view вызываем PSSetShaderResources (вместо SetTexture) и OMSetRenderTargets (вместо SetRenderTarget). Стоит отметить, что у одного ресурса может быть несколько resource views.

Такой принцип позволяет работать обобщенно. Существуют «бестипные» (typeless) ресурсы, то есть ресурсы, которые не имеют определённого типа (не указан при создании) — например, DXGI_FORMAT_R32G32B32_TYPELESS. Тип таких ресурсов выбирается во время создания view (например, DXGI_FORMAT_R32G32B32_UINT или DXGI_FORMAT_R32G32B32_FLOAT) и выбора элемента/слайса из массива текстур/объёмной текстуры.

Использование буферов констант

Set*ShaderConstant заменены на Constant Buffers — группы констант (буфер на n констант), устанавливающихся за раз. Группу можно блокировать и записывать как обычный буфер. Привязка к шейдеру производится начиная с некоторого слота.

Таким образом использование констант сводится к разделению их на несколько групп по частоте обновления (per-object, per-material, per-pass, per-scene) и созданию для каждой группы Constant Buffer. Помимо дополнительной производительности такой подход даёт драйверу высокоуровневую картину — больше возможностей для оптимизации.

Параметры шейдеров

VertexDeclaration заменён на Input Layout. Он требует при создании Shader Input Signature, то есть список input(входных)-параметров шейдера. Созданный объект можно использовать как Vertex Declaration с любым шейдером, имеющим такой же список input-параметров. В D3D9 Vertex Declaration устанавливался независимо от шейдера при рендере и поэтому драйверам приходилось серьёзно модифицировать сетап при смене vdecl. Сейчас vdecl жёстко привязан ко входу шейдера, что позволяет драйверу предвычислять все заранее.

Убраны asm-шейдеры

Шейдеры больше нельзя писать на ассемблере — нужно пользоваться HLSL. Хотя ассемблер для shader model 4.x есть и можно смотреть результат компиляции шейдеров в него, но больше нет возможности получить бинарный код шейдера из текста ассемблера (то что делали psa.exe/vsa.exe). Отреверсинженирить бинарный код, впрочем, никто не мешает.

Компилятор HLSL 4.0

Чтобы было легче портировать код шейдеров, компилятор умеет компилировать HLSL-шейдеры старых версий (SM2.0, SM 3.0) в SM4.0. В новом HLSL добавили атрибуты для хинтов компилятору — размотку циклов и выбор dynamic vs static branching для условных переходов.

Эволюционные изменения в шейдерах

В Shader Model 4 добавлены целочисленные инструкции и битовые операции (можно считать в честном fixed point и передавать булевые флажки), убрано ограничение на количество инструкций (но очень длинный шейдер может упереться в ограничение по времени выполнения пакета на GPU - 10 сек)

Геометрические шейдеры (Geometry Shader)

Геометрический шейдер — дополнительный шейдер между вершинным (Vertex Shader) и пиксельным (Pixel Shader), который может генерировать примитивы. На вход ему подается примитив с информацией о соседях, на выход — можно сгенерировать несколько (не фиксированное число).

Stream Out

Это возможность записывать результат работы Vertex Shader/Geometry Shader в память. Например, кешировать обработку геометрии или вообще геометрию, созданную GS. Можно считать итеративные эффекты, типа Cloth/Water. То есть теперь можно напрямую трансформить и записывать геометрию на GPU, а не только рисовать пиксели в Render Target. Также есть возможность читать в шейдере из буфера в памяти по индексу, то есть иметь достаточно большую read-only shared memory. NV например предлагает там константы анимации хранить для инстансинга.

Уменьшение количества draw calls и переключений состояний

Появились массивы текстур, то есть контейнер одинаковых по размеру и формату текстур, из которого шейдер может выбирать по индексу (в DX10.1 — можно и cubemap arrays). Это тот самый atlasing done right — раньше когда в одной текстуре хранили несколько разных, приходилось беспокоиться за мип-левелы, оставлять зазор между текстурами и т. д. Теперь не надо. В шейдер приходят primitive/instance id, в зависимости от instance ID можно использовать другой набор текстур/координат/каких-либо данных. Ожидается, что dynamic branch в шейдере быстрый (лучше, чем в DX9-hardware), поэтому можно передавать Material ID и выбирать материала в шейдере. То есть, в теории, можно за один вызов генерировать большое количество геометрии с разными параметрами, текстурами и материалами. На практике, dynamic branch имеет довольно-таки большую стоимость по времени и ряд других проблем проблем (вычисление градиентов текстурных координат).

Multi-sampling antialiasing features

Одно из наиболее полезных нововведений, ради которого многие перешли на DX10. Теперь в шейдере можно читать каждый MSAA-семпл отдельно, то есть писать свой собственный AA-фильтр, семплить при процессинге без лишних проблем и даже использовать MSAA RT как текстуру. Кроме того, теперь официально присутствует AlphaToCoverage. В D3D10.1 эти возможности появились и у depth textures.

Поддержка depth textures

Теперь depth buffer можно использовать как текстуру. Можно сказать, чтобы при семплинге сравнивал со значением и делал фильтрацию соседей, можно получить чистый depth value и stencil value.

Другие интересные возможности

  • есть рендер в volume texture
  • в DX10.1 можно скопировать из обычной текстуры в сжатую на GPU
  • есть настоящий conditional render, то есть возможность уменьшить количество draw call по результатам работы GPU асинхронно (можно делать occlusion culling полноценно)

Дополнительные факты

Операционная система Windows XP не поддерживает DX10. Причина в том, что перенос новой драйверной модели невозможен — требуется слишком много изменений в ядре операционной системы. Если же переносить только набор новых функциональных возможностей DX10, то тоже возникают проблемы: виртуализацию и шедулинг невозможно осуществить в старой модели драйвера, перенос аппаратных возможностей — слишком большой объём работы для Microsoft и IHV.

См. также

Напишите отзыв о статье "Direct3D 10"

Ссылки

  • Александр Корень. [itc.ua/node/27196 DirectX 10 – десятый шаг навстречу виртуальному миру]. еженедельник «Компьютерное Обозрение» (16 февраля 2007 года). Проверено 2 августа 2009. [www.webcitation.org/66E3lSotl Архивировано из первоисточника 17 марта 2012].
  • Александр Будик. [www.3dnews.ru/news/dlya_podderzhki_dx10_videokarta_nuzhna_ne_vsegda/ Для поддержки DX10 видеокарта нужна не всегда?]. 3DNews (2 декабря 2008 года). Проверено 2 декабря 2008.

Отрывок, характеризующий Direct3D 10

Опять поднялась занавесь. Анатоль вышел из ложи, спокойный и веселый. Наташа вернулась к отцу в ложу, совершенно уже подчиненная тому миру, в котором она находилась. Всё, что происходило перед ней, уже казалось ей вполне естественным; но за то все прежние мысли ее о женихе, о княжне Марье, о деревенской жизни ни разу не пришли ей в голову, как будто всё то было давно, давно прошедшее.
В четвертом акте был какой то чорт, который пел, махая рукою до тех пор, пока не выдвинули под ним доски, и он не опустился туда. Наташа только это и видела из четвертого акта: что то волновало и мучило ее, и причиной этого волнения был Курагин, за которым она невольно следила глазами. Когда они выходили из театра, Анатоль подошел к ним, вызвал их карету и подсаживал их. Подсаживая Наташу, он пожал ей руку выше локтя. Наташа, взволнованная и красная, оглянулась на него. Он, блестя своими глазами и нежно улыбаясь, смотрел на нее.

Только приехав домой, Наташа могла ясно обдумать всё то, что с ней было, и вдруг вспомнив князя Андрея, она ужаснулась, и при всех за чаем, за который все сели после театра, громко ахнула и раскрасневшись выбежала из комнаты. – «Боже мой! Я погибла! сказала она себе. Как я могла допустить до этого?» думала она. Долго она сидела закрыв раскрасневшееся лицо руками, стараясь дать себе ясный отчет в том, что было с нею, и не могла ни понять того, что с ней было, ни того, что она чувствовала. Всё казалось ей темно, неясно и страшно. Там, в этой огромной, освещенной зале, где по мокрым доскам прыгал под музыку с голыми ногами Duport в курточке с блестками, и девицы, и старики, и голая с спокойной и гордой улыбкой Элен в восторге кричали браво, – там под тенью этой Элен, там это было всё ясно и просто; но теперь одной, самой с собой, это было непонятно. – «Что это такое? Что такое этот страх, который я испытывала к нему? Что такое эти угрызения совести, которые я испытываю теперь»? думала она.
Одной старой графине Наташа в состоянии была бы ночью в постели рассказать всё, что она думала. Соня, она знала, с своим строгим и цельным взглядом, или ничего бы не поняла, или ужаснулась бы ее признанию. Наташа одна сама с собой старалась разрешить то, что ее мучило.
«Погибла ли я для любви князя Андрея или нет? спрашивала она себя и с успокоительной усмешкой отвечала себе: Что я за дура, что я спрашиваю это? Что ж со мной было? Ничего. Я ничего не сделала, ничем не вызвала этого. Никто не узнает, и я его не увижу больше никогда, говорила она себе. Стало быть ясно, что ничего не случилось, что не в чем раскаиваться, что князь Андрей может любить меня и такою . Но какою такою ? Ах Боже, Боже мой! зачем его нет тут»! Наташа успокоивалась на мгновенье, но потом опять какой то инстинкт говорил ей, что хотя всё это и правда и хотя ничего не было – инстинкт говорил ей, что вся прежняя чистота любви ее к князю Андрею погибла. И она опять в своем воображении повторяла весь свой разговор с Курагиным и представляла себе лицо, жесты и нежную улыбку этого красивого и смелого человека, в то время как он пожал ее руку.


Анатоль Курагин жил в Москве, потому что отец отослал его из Петербурга, где он проживал больше двадцати тысяч в год деньгами и столько же долгами, которые кредиторы требовали с отца.
Отец объявил сыну, что он в последний раз платит половину его долгов; но только с тем, чтобы он ехал в Москву в должность адъютанта главнокомандующего, которую он ему выхлопотал, и постарался бы там наконец сделать хорошую партию. Он указал ему на княжну Марью и Жюли Карагину.
Анатоль согласился и поехал в Москву, где остановился у Пьера. Пьер принял Анатоля сначала неохотно, но потом привык к нему, иногда ездил с ним на его кутежи и, под предлогом займа, давал ему деньги.
Анатоль, как справедливо говорил про него Шиншин, с тех пор как приехал в Москву, сводил с ума всех московских барынь в особенности тем, что он пренебрегал ими и очевидно предпочитал им цыганок и французских актрис, с главою которых – mademoiselle Georges, как говорили, он был в близких сношениях. Он не пропускал ни одного кутежа у Данилова и других весельчаков Москвы, напролет пил целые ночи, перепивая всех, и бывал на всех вечерах и балах высшего света. Рассказывали про несколько интриг его с московскими дамами, и на балах он ухаживал за некоторыми. Но с девицами, в особенности с богатыми невестами, которые были большей частью все дурны, он не сближался, тем более, что Анатоль, чего никто не знал, кроме самых близких друзей его, был два года тому назад женат. Два года тому назад, во время стоянки его полка в Польше, один польский небогатый помещик заставил Анатоля жениться на своей дочери.
Анатоль весьма скоро бросил свою жену и за деньги, которые он условился высылать тестю, выговорил себе право слыть за холостого человека.
Анатоль был всегда доволен своим положением, собою и другими. Он был инстинктивно всем существом своим убежден в том, что ему нельзя было жить иначе, чем как он жил, и что он никогда в жизни не сделал ничего дурного. Он не был в состоянии обдумать ни того, как его поступки могут отозваться на других, ни того, что может выйти из такого или такого его поступка. Он был убежден, что как утка сотворена так, что она всегда должна жить в воде, так и он сотворен Богом так, что должен жить в тридцать тысяч дохода и занимать всегда высшее положение в обществе. Он так твердо верил в это, что, глядя на него, и другие были убеждены в этом и не отказывали ему ни в высшем положении в свете, ни в деньгах, которые он, очевидно, без отдачи занимал у встречного и поперечного.
Он не был игрок, по крайней мере никогда не желал выигрыша. Он не был тщеславен. Ему было совершенно всё равно, что бы об нем ни думали. Еще менее он мог быть повинен в честолюбии. Он несколько раз дразнил отца, портя свою карьеру, и смеялся над всеми почестями. Он был не скуп и не отказывал никому, кто просил у него. Одно, что он любил, это было веселье и женщины, и так как по его понятиям в этих вкусах не было ничего неблагородного, а обдумать то, что выходило для других людей из удовлетворения его вкусов, он не мог, то в душе своей он считал себя безукоризненным человеком, искренно презирал подлецов и дурных людей и с спокойной совестью высоко носил голову.
У кутил, у этих мужских магдалин, есть тайное чувство сознания невинности, такое же, как и у магдалин женщин, основанное на той же надежде прощения. «Ей всё простится, потому что она много любила, и ему всё простится, потому что он много веселился».
Долохов, в этом году появившийся опять в Москве после своего изгнания и персидских похождений, и ведший роскошную игорную и кутежную жизнь, сблизился с старым петербургским товарищем Курагиным и пользовался им для своих целей.
Анатоль искренно любил Долохова за его ум и удальство. Долохов, которому были нужны имя, знатность, связи Анатоля Курагина для приманки в свое игорное общество богатых молодых людей, не давая ему этого чувствовать, пользовался и забавлялся Курагиным. Кроме расчета, по которому ему был нужен Анатоль, самый процесс управления чужою волей был наслаждением, привычкой и потребностью для Долохова.
Наташа произвела сильное впечатление на Курагина. Он за ужином после театра с приемами знатока разобрал перед Долоховым достоинство ее рук, плеч, ног и волос, и объявил свое решение приволокнуться за нею. Что могло выйти из этого ухаживанья – Анатоль не мог обдумать и знать, как он никогда не знал того, что выйдет из каждого его поступка.
– Хороша, брат, да не про нас, – сказал ему Долохов.
– Я скажу сестре, чтобы она позвала ее обедать, – сказал Анатоль. – А?
– Ты подожди лучше, когда замуж выйдет…
– Ты знаешь, – сказал Анатоль, – j'adore les petites filles: [обожаю девочек:] – сейчас потеряется.
– Ты уж попался раз на petite fille [девочке], – сказал Долохов, знавший про женитьбу Анатоля. – Смотри!
– Ну уж два раза нельзя! А? – сказал Анатоль, добродушно смеясь.


Следующий после театра день Ростовы никуда не ездили и никто не приезжал к ним. Марья Дмитриевна о чем то, скрывая от Наташи, переговаривалась с ее отцом. Наташа догадывалась, что они говорили о старом князе и что то придумывали, и ее беспокоило и оскорбляло это. Она всякую минуту ждала князя Андрея, и два раза в этот день посылала дворника на Вздвиженку узнавать, не приехал ли он. Он не приезжал. Ей было теперь тяжеле, чем первые дни своего приезда. К нетерпению и грусти ее о нем присоединились неприятное воспоминание о свидании с княжной Марьей и с старым князем, и страх и беспокойство, которым она не знала причины. Ей всё казалось, что или он никогда не приедет, или что прежде, чем он приедет, с ней случится что нибудь. Она не могла, как прежде, спокойно и продолжительно, одна сама с собой думать о нем. Как только она начинала думать о нем, к воспоминанию о нем присоединялось воспоминание о старом князе, о княжне Марье и о последнем спектакле, и о Курагине. Ей опять представлялся вопрос, не виновата ли она, не нарушена ли уже ее верность князю Андрею, и опять она заставала себя до малейших подробностей воспоминающею каждое слово, каждый жест, каждый оттенок игры выражения на лице этого человека, умевшего возбудить в ней непонятное для нее и страшное чувство. На взгляд домашних, Наташа казалась оживленнее обыкновенного, но она далеко была не так спокойна и счастлива, как была прежде.
В воскресение утром Марья Дмитриевна пригласила своих гостей к обедни в свой приход Успенья на Могильцах.
– Я этих модных церквей не люблю, – говорила она, видимо гордясь своим свободомыслием. – Везде Бог один. Поп у нас прекрасный, служит прилично, так это благородно, и дьякон тоже. Разве от этого святость какая, что концерты на клиросе поют? Не люблю, одно баловство!
Марья Дмитриевна любила воскресные дни и умела праздновать их. Дом ее бывал весь вымыт и вычищен в субботу; люди и она не работали, все были празднично разряжены, и все бывали у обедни. К господскому обеду прибавлялись кушанья, и людям давалась водка и жареный гусь или поросенок. Но ни на чем во всем доме так не бывал заметен праздник, как на широком, строгом лице Марьи Дмитриевны, в этот день принимавшем неизменяемое выражение торжественности.
Когда напились кофе после обедни, в гостиной с снятыми чехлами, Марье Дмитриевне доложили, что карета готова, и она с строгим видом, одетая в парадную шаль, в которой она делала визиты, поднялась и объявила, что едет к князю Николаю Андреевичу Болконскому, чтобы объясниться с ним насчет Наташи.
После отъезда Марьи Дмитриевны, к Ростовым приехала модистка от мадам Шальме, и Наташа, затворив дверь в соседней с гостиной комнате, очень довольная развлечением, занялась примериваньем новых платьев. В то время как она, надев сметанный на живую нитку еще без рукавов лиф и загибая голову, гляделась в зеркало, как сидит спинка, она услыхала в гостиной оживленные звуки голоса отца и другого, женского голоса, который заставил ее покраснеть. Это был голос Элен. Не успела Наташа снять примериваемый лиф, как дверь отворилась и в комнату вошла графиня Безухая, сияющая добродушной и ласковой улыбкой, в темнолиловом, с высоким воротом, бархатном платье.
– Ah, ma delicieuse! [О, моя прелестная!] – сказала она красневшей Наташе. – Charmante! [Очаровательна!] Нет, это ни на что не похоже, мой милый граф, – сказала она вошедшему за ней Илье Андреичу. – Как жить в Москве и никуда не ездить? Нет, я от вас не отстану! Нынче вечером у меня m lle Georges декламирует и соберутся кое кто; и если вы не привезете своих красавиц, которые лучше m lle Georges, то я вас знать не хочу. Мужа нет, он уехал в Тверь, а то бы я его за вами прислала. Непременно приезжайте, непременно, в девятом часу. – Она кивнула головой знакомой модистке, почтительно присевшей ей, и села на кресло подле зеркала, живописно раскинув складки своего бархатного платья. Она не переставала добродушно и весело болтать, беспрестанно восхищаясь красотой Наташи. Она рассмотрела ее платья и похвалила их, похвалилась и своим новым платьем en gaz metallique, [из газа цвета металла,] которое она получила из Парижа и советовала Наташе сделать такое же.