forked from python-openxml/python-docx
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathtest_shape.py
183 lines (147 loc) · 6.44 KB
/
test_shape.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
# encoding: utf-8
"""
Test suite for the docx.shape module
"""
from __future__ import absolute_import, print_function, unicode_literals
import pytest
from docx.enum.shape import WD_INLINE_SHAPE
from docx.oxml.ns import nsmap
from docx.shape import InlineShape, InlineShapes
from docx.shared import Length
from .oxml.unitdata.dml import (
a_blip, a_blipFill, a_graphic, a_graphicData, a_pic, an_inline,
)
from .unitutil.cxml import element, xml
from .unitutil.mock import loose_mock
class DescribeInlineShapes(object):
def it_knows_how_many_inline_shapes_it_contains(
self, inline_shapes_fixture):
inline_shapes, expected_count = inline_shapes_fixture
assert len(inline_shapes) == expected_count
def it_can_iterate_over_its_InlineShape_instances(
self, inline_shapes_fixture):
inline_shapes, inline_shape_count = inline_shapes_fixture
actual_count = 0
for inline_shape in inline_shapes:
assert isinstance(inline_shape, InlineShape)
actual_count += 1
assert actual_count == inline_shape_count
def it_provides_indexed_access_to_inline_shapes(
self, inline_shapes_fixture):
inline_shapes, inline_shape_count = inline_shapes_fixture
for idx in range(-inline_shape_count, inline_shape_count):
inline_shape = inline_shapes[idx]
assert isinstance(inline_shape, InlineShape)
def it_raises_on_indexed_access_out_of_range(
self, inline_shapes_fixture):
inline_shapes, inline_shape_count = inline_shapes_fixture
with pytest.raises(IndexError):
too_low = -1 - inline_shape_count
inline_shapes[too_low]
with pytest.raises(IndexError):
too_high = inline_shape_count
inline_shapes[too_high]
def it_knows_the_part_it_belongs_to(self, inline_shapes_with_parent_):
inline_shapes, parent_ = inline_shapes_with_parent_
part = inline_shapes.part
assert part is parent_.part
# fixtures -------------------------------------------------------
@pytest.fixture
def inline_shapes_fixture(self):
body = element(
'w:body/w:p/(w:r/w:drawing/wp:inline, w:r/w:drawing/wp:inline)'
)
inline_shapes = InlineShapes(body, None)
expected_count = 2
return inline_shapes, expected_count
# fixture components ---------------------------------------------
@pytest.fixture
def inline_shapes_with_parent_(self, request):
parent_ = loose_mock(request, name='parent_')
inline_shapes = InlineShapes(None, parent_)
return inline_shapes, parent_
class DescribeInlineShape(object):
def it_knows_what_type_of_shape_it_is(self, shape_type_fixture):
inline_shape, inline_shape_type = shape_type_fixture
assert inline_shape.type == inline_shape_type
def it_knows_its_display_dimensions(self, dimensions_get_fixture):
inline_shape, cx, cy = dimensions_get_fixture
width = inline_shape.width
height = inline_shape.height
assert isinstance(width, Length)
assert width == cx
assert isinstance(height, Length)
assert height == cy
def it_can_change_its_display_dimensions(self, dimensions_set_fixture):
inline_shape, cx, cy, expected_xml = dimensions_set_fixture
inline_shape.width = cx
inline_shape.height = cy
assert inline_shape._inline.xml == expected_xml
# fixtures -------------------------------------------------------
@pytest.fixture
def dimensions_get_fixture(self):
inline_cxml, expected_cx, expected_cy = (
'wp:inline/wp:extent{cx=333, cy=666}', 333, 666
)
inline_shape = InlineShape(element(inline_cxml))
return inline_shape, expected_cx, expected_cy
@pytest.fixture
def dimensions_set_fixture(self):
inline_cxml, new_cx, new_cy, expected_cxml = (
'wp:inline/(wp:extent{cx=333,cy=666},a:graphic/a:graphicData/'
'pic:pic/pic:spPr/a:xfrm/a:ext{cx=333,cy=666})',
444, 888,
'wp:inline/(wp:extent{cx=444,cy=888},a:graphic/a:graphicData/'
'pic:pic/pic:spPr/a:xfrm/a:ext{cx=444,cy=888})'
)
inline_shape = InlineShape(element(inline_cxml))
expected_xml = xml(expected_cxml)
return inline_shape, new_cx, new_cy, expected_xml
@pytest.fixture(params=[
'embed pic', 'link pic', 'link+embed pic', 'chart', 'smart art',
'not implemented'
])
def shape_type_fixture(self, request):
if request.param == 'embed pic':
inline = self._inline_with_picture(embed=True)
shape_type = WD_INLINE_SHAPE.PICTURE
elif request.param == 'link pic':
inline = self._inline_with_picture(link=True)
shape_type = WD_INLINE_SHAPE.LINKED_PICTURE
elif request.param == 'link+embed pic':
inline = self._inline_with_picture(embed=True, link=True)
shape_type = WD_INLINE_SHAPE.LINKED_PICTURE
elif request.param == 'chart':
inline = self._inline_with_uri(nsmap['c'])
shape_type = WD_INLINE_SHAPE.CHART
elif request.param == 'smart art':
inline = self._inline_with_uri(nsmap['dgm'])
shape_type = WD_INLINE_SHAPE.SMART_ART
elif request.param == 'not implemented':
inline = self._inline_with_uri('foobar')
shape_type = WD_INLINE_SHAPE.NOT_IMPLEMENTED
return InlineShape(inline), shape_type
# fixture components ---------------------------------------------
def _inline_with_picture(self, embed=False, link=False):
picture_ns = nsmap['pic']
blip_bldr = a_blip()
if embed:
blip_bldr.with_embed('rId1')
if link:
blip_bldr.with_link('rId2')
inline = (
an_inline().with_nsdecls('wp', 'r').with_child(
a_graphic().with_nsdecls().with_child(
a_graphicData().with_uri(picture_ns).with_child(
a_pic().with_nsdecls().with_child(
a_blipFill().with_child(
blip_bldr)))))
).element
return inline
def _inline_with_uri(self, uri):
inline = (
an_inline().with_nsdecls('wp').with_child(
a_graphic().with_nsdecls().with_child(
a_graphicData().with_uri(uri)))
).element
return inline