Coverage for /pythoncovmergedfiles/medio/medio/usr/local/lib/python3.11/site-packages/xlsxwriter/format.py: 47%

Shortcuts on this page

r m x   toggle line displays

j k   next/prev highlighted chunk

0   (zero) top of page

1   (one) first highlighted chunk

352 statements  

1############################################################################### 

2# 

3# Format - A class for writing the Excel XLSX Worksheet file. 

4# 

5# SPDX-License-Identifier: BSD-2-Clause 

6# 

7# Copyright (c) 2013-2025, John McNamara, jmcnamara@cpan.org 

8# 

9 

10# Package imports. 

11from typing import Literal, Union 

12from warnings import warn 

13 

14from xlsxwriter.color import Color 

15 

16from . import xmlwriter 

17 

18 

19class Format(xmlwriter.XMLwriter): 

20 """ 

21 A class for writing the Excel XLSX Format file. 

22 

23 

24 """ 

25 

26 ########################################################################### 

27 # 

28 # Public API. 

29 # 

30 ########################################################################### 

31 

32 def __init__(self, properties=None, xf_indices=None, dxf_indices=None) -> None: 

33 """ 

34 Constructor. 

35 

36 """ 

37 if properties is None: 

38 properties = {} 

39 

40 super().__init__() 

41 

42 self.xf_format_indices = xf_indices 

43 self.dxf_format_indices = dxf_indices 

44 self.xf_index = None 

45 self.dxf_index = None 

46 

47 self.num_format = "General" 

48 self.num_format_index = 0 

49 self.font_index = 0 

50 self.has_font = False 

51 self.has_dxf_font = False 

52 

53 self.bold = 0 

54 self.underline = 0 

55 self.italic = 0 

56 self.font_name = "Calibri" 

57 self.font_size = 11 

58 self.font_color = None 

59 self.font_strikeout = 0 

60 self.font_outline = 0 

61 self.font_shadow = 0 

62 self.font_script = 0 

63 self.font_family = 2 

64 self.font_charset = 0 

65 self.font_scheme = "minor" 

66 self.font_condense = 0 

67 self.font_extend = 0 

68 self.theme = 0 

69 self.hyperlink = False 

70 self.xf_id = 0 

71 

72 self.hidden = 0 

73 self.locked = 1 

74 

75 self.text_h_align = 0 

76 self.text_wrap = 0 

77 self.text_v_align = 0 

78 self.text_justlast = 0 

79 self.rotation = 0 

80 

81 self.fg_color = None 

82 self.bg_color = None 

83 self.pattern = 0 

84 self.has_fill = False 

85 self.has_dxf_fill = False 

86 self.fill_index = 0 

87 self.fill_count = 0 

88 

89 self.border_index = 0 

90 self.has_border = False 

91 self.has_dxf_border = False 

92 self.border_count = 0 

93 

94 self.bottom = 0 

95 self.bottom_color = None 

96 self.diag_border = 0 

97 self.diag_color = None 

98 self.diag_type = 0 

99 self.left = 0 

100 self.left_color = None 

101 self.right = 0 

102 self.right_color = None 

103 self.top = 0 

104 self.top_color = None 

105 

106 self.indent = 0 

107 self.shrink = 0 

108 self.merge_range = 0 

109 self.reading_order = 0 

110 self.just_distrib = 0 

111 self.color_indexed = 0 

112 self.font_only = 0 

113 

114 self.quote_prefix = False 

115 self.checkbox = False 

116 

117 # Convert properties in the constructor to method calls. 

118 for key, value in properties.items(): 

119 getattr(self, "set_" + key)(value) 

120 

121 self._format_key = None 

122 

123 def __repr__(self) -> str: 

124 """ 

125 Return a string representation of the Format instance. 

126 """ 

127 return ( 

128 f"Format(" 

129 f"font_name={self.font_name!r}, " 

130 f"font_size={self.font_size}, " 

131 f"bold={self.bold}, " 

132 f"italic={self.italic}, " 

133 f"underline={self.underline}, " 

134 f"font_color={self.font_color}, " 

135 f"num_format={self.num_format!r}, " 

136 f"text_h_align={self.text_h_align}, " 

137 f"text_v_align={self.text_v_align}, " 

138 f"fg_color={self.fg_color}, " 

139 f"bg_color={self.bg_color}, " 

140 f"pattern={self.pattern}, " 

141 f"locked={self.locked}, " 

142 f"hidden={self.hidden})" 

143 ) 

144 

145 ########################################################################### 

146 # 

147 # Format properties. 

148 # 

149 ########################################################################### 

150 

151 def set_font_name(self, font_name) -> None: 

152 """ 

153 Set the Format font_name property such as 'Time New Roman'. The 

154 default Excel font is 'Calibri'. 

155 

156 Args: 

157 font_name: String with the font name. No default. 

158 

159 Returns: 

160 Nothing. 

161 

162 """ 

163 self.font_name = font_name 

164 

165 def set_font_size(self, font_size: int = 11) -> None: 

166 """ 

167 Set the Format font_size property. The default Excel font size is 11. 

168 

169 Args: 

170 font_size: Int with font size. No default. 

171 

172 Returns: 

173 Nothing. 

174 

175 """ 

176 self.font_size = font_size 

177 

178 def set_font_color(self, font_color: Union[str, Color]) -> None: 

179 """ 

180 Set the Format font_color property. The Excel default is black. 

181 

182 Args: 

183 font_color: String with the font color. No default. 

184 

185 Returns: 

186 Nothing. 

187 

188 """ 

189 self.font_color = Color._from_value(font_color) 

190 

191 def set_bold(self, bold: bool = True) -> None: 

192 """ 

193 Set the Format bold property. 

194 

195 Args: 

196 bold: Default is True, turns property on. 

197 

198 Returns: 

199 Nothing. 

200 

201 """ 

202 self.bold = bold 

203 

204 def set_italic(self, italic: bool = True) -> None: 

205 """ 

206 Set the Format italic property. 

207 

208 Args: 

209 italic: Default is True, turns property on. 

210 

211 Returns: 

212 Nothing. 

213 

214 """ 

215 self.italic = italic 

216 

217 def set_underline(self, underline: Literal[1, 2, 33, 34] = 1) -> None: 

218 """ 

219 Set the Format underline property. 

220 

221 Args: 

222 underline: Default is 1, single underline. 

223 

224 Returns: 

225 Nothing. 

226 

227 """ 

228 self.underline = underline 

229 

230 def set_font_strikeout(self, font_strikeout: bool = True) -> None: 

231 """ 

232 Set the Format font_strikeout property. 

233 

234 Args: 

235 font_strikeout: Default is True, turns property on. 

236 

237 Returns: 

238 Nothing. 

239 

240 """ 

241 self.font_strikeout = font_strikeout 

242 

243 def set_font_script(self, font_script: Literal[1, 2] = 1) -> None: 

244 """ 

245 Set the Format font_script property. 

246 

247 Args: 

248 font_script: Default is 1, superscript. 

249 

250 Returns: 

251 Nothing. 

252 

253 """ 

254 self.font_script = font_script 

255 

256 def set_font_outline(self, font_outline: bool = True) -> None: 

257 """ 

258 Set the Format font_outline property. 

259 

260 Args: 

261 font_outline: Default is True, turns property on. 

262 

263 Returns: 

264 Nothing. 

265 

266 """ 

267 self.font_outline = font_outline 

268 

269 def set_font_shadow(self, font_shadow: bool = True) -> None: 

270 """ 

271 Set the Format font_shadow property. 

272 

273 Args: 

274 font_shadow: Default is True, turns property on. 

275 

276 Returns: 

277 Nothing. 

278 

279 """ 

280 self.font_shadow = font_shadow 

281 

282 def set_num_format(self, num_format: str) -> None: 

283 """ 

284 Set the Format num_format property such as '#,##0'. 

285 

286 Args: 

287 num_format: String representing the number format. No default. 

288 

289 Returns: 

290 Nothing. 

291 

292 """ 

293 self.num_format = num_format 

294 

295 def set_locked(self, locked: bool = True) -> None: 

296 """ 

297 Set the Format locked property. 

298 

299 Args: 

300 locked: Default is True, turns property on. 

301 

302 Returns: 

303 Nothing. 

304 

305 """ 

306 self.locked = locked 

307 

308 def set_hidden(self, hidden: bool = True) -> None: 

309 """ 

310 Set the Format hidden property. 

311 

312 Args: 

313 hidden: Default is True, turns property on. 

314 

315 Returns: 

316 Nothing. 

317 

318 """ 

319 self.hidden = hidden 

320 

321 def set_align( 

322 self, 

323 alignment: Literal[ 

324 "left", 

325 "centre", 

326 "center", 

327 "right", 

328 "fill", 

329 "justify", 

330 "center_across", 

331 "centre_across", 

332 "distributed", 

333 "justify_distributed", 

334 "justify_distributed", 

335 "top", 

336 "vcentre", 

337 "vcenter", 

338 "bottom", 

339 "vjustify", 

340 "vdistributed", 

341 ], 

342 ) -> None: 

343 """ 

344 Set the Format cell alignment. 

345 

346 Args: 

347 alignment: String representing alignment. No default. 

348 

349 Returns: 

350 Nothing. 

351 """ 

352 alignment = alignment.lower() 

353 

354 # Set horizontal alignment properties. 

355 if alignment == "left": 

356 self.set_text_h_align(1) 

357 if alignment == "centre": 

358 self.set_text_h_align(2) 

359 if alignment == "center": 

360 self.set_text_h_align(2) 

361 if alignment == "right": 

362 self.set_text_h_align(3) 

363 if alignment == "fill": 

364 self.set_text_h_align(4) 

365 if alignment == "justify": 

366 self.set_text_h_align(5) 

367 if alignment == "center_across": 

368 self.set_text_h_align(6) 

369 if alignment == "centre_across": 

370 self.set_text_h_align(6) 

371 if alignment == "distributed": 

372 self.set_text_h_align(7) 

373 if alignment == "justify_distributed": 

374 self.set_text_h_align(7) 

375 

376 if alignment == "justify_distributed": 

377 self.just_distrib = 1 

378 

379 # Set vertical alignment properties. 

380 if alignment == "top": 

381 self.set_text_v_align(1) 

382 if alignment == "vcentre": 

383 self.set_text_v_align(2) 

384 if alignment == "vcenter": 

385 self.set_text_v_align(2) 

386 if alignment == "bottom": 

387 self.set_text_v_align(3) 

388 if alignment == "vjustify": 

389 self.set_text_v_align(4) 

390 if alignment == "vdistributed": 

391 self.set_text_v_align(5) 

392 

393 def set_center_across(self, align_type: None = None) -> None: 

394 # pylint: disable=unused-argument 

395 """ 

396 Set the Format center_across property. 

397 

398 Returns: 

399 Nothing. 

400 

401 """ 

402 self.set_text_h_align(6) 

403 

404 def set_text_wrap(self, text_wrap: bool = True) -> None: 

405 """ 

406 Set the Format text_wrap property. 

407 

408 Args: 

409 text_wrap: Default is True, turns property on. 

410 

411 Returns: 

412 Nothing. 

413 

414 """ 

415 self.text_wrap = text_wrap 

416 

417 def set_rotation(self, rotation: int) -> None: 

418 """ 

419 Set the Format rotation property. 

420 

421 Args: 

422 rotation: Rotation angle. No default. 

423 

424 Returns: 

425 Nothing. 

426 

427 """ 

428 rotation = int(rotation) 

429 

430 # Map user angle to Excel angle. 

431 if rotation == 270: 

432 rotation = 255 

433 elif -90 <= rotation <= 90: 

434 if rotation < 0: 

435 rotation = -rotation + 90 

436 else: 

437 warn("Rotation rotation outside range: -90 <= angle <= 90") 

438 return 

439 

440 self.rotation = rotation 

441 

442 def set_indent(self, indent: int = 1) -> None: 

443 """ 

444 Set the Format indent property. 

445 

446 Args: 

447 indent: Default is 1, first indentation level. 

448 

449 Returns: 

450 Nothing. 

451 

452 """ 

453 self.indent = indent 

454 

455 def set_shrink(self, shrink: bool = True) -> None: 

456 """ 

457 Set the Format shrink property. 

458 

459 Args: 

460 shrink: Default is True, turns property on. 

461 

462 Returns: 

463 Nothing. 

464 

465 """ 

466 self.shrink = shrink 

467 

468 def set_text_justlast(self, text_justlast: bool = True) -> None: 

469 """ 

470 Set the Format text_justlast property. 

471 

472 Args: 

473 text_justlast: Default is True, turns property on. 

474 

475 Returns: 

476 Nothing. 

477 

478 """ 

479 self.text_justlast = text_justlast 

480 

481 def set_pattern(self, pattern: int = 1) -> None: 

482 """ 

483 Set the Format pattern property. 

484 

485 Args: 

486 pattern: Default is 1, solid fill. 

487 

488 Returns: 

489 Nothing. 

490 

491 """ 

492 self.pattern = pattern 

493 

494 def set_bg_color(self, bg_color: Union[str, Color]) -> None: 

495 """ 

496 Set the Format bg_color property. 

497 

498 Args: 

499 bg_color: Background color. No default. 

500 

501 Returns: 

502 Nothing. 

503 

504 """ 

505 self.bg_color = Color._from_value(bg_color) 

506 

507 def set_fg_color(self, fg_color: Union[str, Color]) -> None: 

508 """ 

509 Set the Format fg_color property. 

510 

511 Args: 

512 fg_color: Foreground color. No default. 

513 

514 Returns: 

515 Nothing. 

516 

517 """ 

518 self.fg_color = Color._from_value(fg_color) 

519 

520 # set_border(style) Set cells borders to the same style 

521 def set_border(self, style: int = 1) -> None: 

522 """ 

523 Set the Format bottom property. 

524 

525 Args: 

526 bottom: Default is 1, border type 1. 

527 

528 Returns: 

529 Nothing. 

530 

531 """ 

532 self.set_bottom(style) 

533 self.set_top(style) 

534 self.set_left(style) 

535 self.set_right(style) 

536 

537 # set_border_color(color) Set cells border to the same color 

538 def set_border_color(self, color: Union[str, Color]) -> None: 

539 """ 

540 Set the Format bottom property. 

541 

542 Args: 

543 color: Color string. No default. 

544 

545 Returns: 

546 Nothing. 

547 

548 """ 

549 self.set_bottom_color(color) 

550 self.set_top_color(color) 

551 self.set_left_color(color) 

552 self.set_right_color(color) 

553 

554 def set_bottom(self, bottom: int = 1) -> None: 

555 """ 

556 Set the Format bottom property. 

557 

558 Args: 

559 bottom: Default is 1, border type 1. 

560 

561 Returns: 

562 Nothing. 

563 

564 """ 

565 self.bottom = bottom 

566 

567 def set_bottom_color(self, bottom_color: Union[str, Color]) -> None: 

568 """ 

569 Set the Format bottom_color property. 

570 

571 Args: 

572 bottom_color: Color string. No default. 

573 

574 Returns: 

575 Nothing. 

576 

577 """ 

578 self.bottom_color = Color._from_value(bottom_color) 

579 

580 def set_diag_type(self, diag_type: Literal[1, 2, 3] = 1) -> None: 

581 """ 

582 Set the Format diag_type property. 

583 

584 Args: 

585 diag_type: Default is 1, border type 1. 

586 

587 Returns: 

588 Nothing. 

589 

590 """ 

591 self.diag_type = diag_type 

592 

593 def set_left(self, left: int = 1) -> None: 

594 """ 

595 Set the Format left property. 

596 

597 Args: 

598 left: Default is 1, border type 1. 

599 

600 Returns: 

601 Nothing. 

602 

603 """ 

604 self.left = left 

605 

606 def set_left_color(self, left_color: Union[str, Color]) -> None: 

607 """ 

608 Set the Format left_color property. 

609 

610 Args: 

611 left_color: Color string. No default. 

612 

613 Returns: 

614 Nothing. 

615 

616 """ 

617 self.left_color = Color._from_value(left_color) 

618 

619 def set_right(self, right: int = 1) -> None: 

620 """ 

621 Set the Format right property. 

622 

623 Args: 

624 right: Default is 1, border type 1. 

625 

626 Returns: 

627 Nothing. 

628 

629 """ 

630 self.right = right 

631 

632 def set_right_color(self, right_color: Union[str, Color]) -> None: 

633 """ 

634 Set the Format right_color property. 

635 

636 Args: 

637 right_color: Color string. No default. 

638 

639 Returns: 

640 Nothing. 

641 

642 """ 

643 self.right_color = Color._from_value(right_color) 

644 

645 def set_top(self, top: int = 1) -> None: 

646 """ 

647 Set the Format top property. 

648 

649 Args: 

650 top: Default is 1, border type 1. 

651 

652 Returns: 

653 Nothing. 

654 

655 """ 

656 self.top = top 

657 

658 def set_top_color(self, top_color: Union[str, Color]) -> None: 

659 """ 

660 Set the Format top_color property. 

661 

662 Args: 

663 top_color: Color string. No default. 

664 

665 Returns: 

666 Nothing. 

667 

668 """ 

669 self.top_color = Color._from_value(top_color) 

670 

671 def set_diag_color(self, diag_color: Union[str, Color]) -> None: 

672 """ 

673 Set the Format diag_color property. 

674 

675 Args: 

676 diag_color: Color string. No default. 

677 

678 Returns: 

679 Nothing. 

680 

681 """ 

682 self.diag_color = Color._from_value(diag_color) 

683 

684 def set_diag_border(self, diag_border: int = 1) -> None: 

685 """ 

686 Set the Format diag_border property. 

687 

688 Args: 

689 diag_border: Default is 1, border type 1. 

690 

691 Returns: 

692 Nothing. 

693 

694 """ 

695 self.diag_border = diag_border 

696 

697 def set_quote_prefix(self, quote_prefix: bool = True) -> None: 

698 """ 

699 Set the Format quote prefix property. 

700 

701 Args: 

702 quote_prefix: Default is True, turns property on. 

703 

704 Returns: 

705 Nothing. 

706 

707 """ 

708 self.quote_prefix = quote_prefix 

709 

710 def set_checkbox(self, checkbox: bool = True) -> None: 

711 """ 

712 Set the Format property to show a checkbox in a cell. 

713 

714 This format property can be used with a cell that contains a boolean 

715 value to display it as a checkbox. This property isn't required very 

716 often and it is generally easier to create a checkbox using the 

717 ``worksheet.insert_checkbox()`` method. 

718 

719 Args: 

720 checkbox: Default is True, turns property on. 

721 

722 Returns: 

723 Nothing. 

724 

725 """ 

726 self.checkbox = checkbox 

727 

728 ########################################################################### 

729 # 

730 # Internal Format properties. These aren't documented since they are 

731 # either only used internally or else are unlikely to be set by the user. 

732 # 

733 ########################################################################### 

734 

735 def set_has_font(self, has_font: bool = True) -> None: 

736 """ 

737 Set the property to indicate the format has a font. 

738 

739 Args: 

740 has_font: Default is True, turns property on. 

741 

742 Returns: 

743 Nothing. 

744 

745 """ 

746 self.has_font = has_font 

747 

748 def set_has_fill(self, has_fill: bool = True) -> None: 

749 """ 

750 Set the property to indicate the format has a fill. 

751 

752 Args: 

753 has_fill: Default is True, turns property on. 

754 

755 Returns: 

756 Nothing. 

757 

758 """ 

759 self.has_fill = has_fill 

760 

761 def set_font_index(self, font_index: int) -> None: 

762 """ 

763 Set the unique font index property. 

764 

765 Args: 

766 font_index: The unique font index. 

767 

768 Returns: 

769 Nothing. 

770 

771 """ 

772 self.font_index = font_index 

773 

774 def set_xf_index(self, xf_index: int) -> None: 

775 """ 

776 Set the unique format index property. 

777 

778 Args: 

779 xf_index: The unique Excel format index. 

780 

781 Returns: 

782 Nothing. 

783 

784 """ 

785 self.xf_index = xf_index 

786 

787 def set_dxf_index(self, dxf_index: int) -> None: 

788 """ 

789 Set the unique conditional format index property. 

790 

791 Args: 

792 dxf_index: The unique Excel conditional format index. 

793 

794 Returns: 

795 Nothing. 

796 

797 """ 

798 self.dxf_index = dxf_index 

799 

800 def set_num_format_index(self, num_format_index: int) -> None: 

801 """ 

802 Set the number format_index property. 

803 

804 Args: 

805 num_format_index: The unique number format index. 

806 

807 Returns: 

808 Nothing. 

809 

810 """ 

811 self.num_format_index = num_format_index 

812 

813 def set_text_h_align(self, text_h_align: int) -> None: 

814 """ 

815 Set the horizontal text alignment property. 

816 

817 Args: 

818 text_h_align: Horizontal text alignment. 

819 

820 Returns: 

821 Nothing. 

822 

823 """ 

824 self.text_h_align = text_h_align 

825 

826 def set_text_v_align(self, text_v_align: int) -> None: 

827 """ 

828 Set the vertical text alignment property. 

829 

830 Args: 

831 text_h_align: Vertical text alignment. 

832 

833 Returns: 

834 Nothing. 

835 

836 """ 

837 self.text_v_align = text_v_align 

838 

839 def set_reading_order(self, direction: int = 0) -> None: 

840 # Set the reading_order property. 

841 """ 

842 Set the reading order property. 

843 

844 Args: 

845 direction: Default is 0, left to right. 

846 

847 Returns: 

848 Nothing. 

849 

850 """ 

851 self.reading_order = direction 

852 

853 def set_valign( 

854 self, 

855 align: Literal[ 

856 "left", 

857 "centre", 

858 "center", 

859 "right", 

860 "fill", 

861 "justify", 

862 "center_across", 

863 "centre_across", 

864 "distributed", 

865 "justify_distributed", 

866 "justify_distributed", 

867 "top", 

868 "vcentre", 

869 "vcenter", 

870 "bottom", 

871 "vjustify", 

872 "vdistributed", 

873 ], 

874 ) -> None: 

875 # Set vertical cell alignment. This is required by the constructor 

876 # properties dict to differentiate between the vertical and horizontal 

877 # properties. 

878 """ 

879 Set vertical cell alignment property. 

880 

881 This is required by the constructor properties dict to differentiate 

882 between the vertical and horizontal properties. 

883 

884 Args: 

885 align: Alignment property. 

886 

887 Returns: 

888 Nothing. 

889 

890 """ 

891 self.set_align(align) 

892 

893 def set_font_family(self, font_family: int) -> None: 

894 """ 

895 Set the font family property. 

896 

897 Args: 

898 font_family: Font family number. 

899 

900 Returns: 

901 Nothing. 

902 

903 """ 

904 self.font_family = font_family 

905 

906 def set_font_charset(self, font_charset: int) -> None: 

907 """ 

908 Set the font character set property. 

909 

910 Args: 

911 font_charset: The font character set number. 

912 

913 Returns: 

914 Nothing. 

915 

916 """ 

917 self.font_charset = font_charset 

918 

919 def set_font_scheme(self, font_scheme: int) -> None: 

920 """ 

921 Set the font scheme property. 

922 

923 Args: 

924 font_scheme: The font scheme. 

925 

926 Returns: 

927 Nothing. 

928 

929 """ 

930 self.font_scheme = font_scheme 

931 

932 def set_font_condense(self, font_condense: int) -> None: 

933 """ 

934 Set the font condense property. 

935 

936 Args: 

937 font_condense: The font condense property. 

938 

939 Returns: 

940 Nothing. 

941 

942 """ 

943 self.font_condense = font_condense 

944 

945 def set_font_extend(self, font_extend: int) -> None: 

946 """ 

947 Set the font extend property. 

948 

949 Args: 

950 font_extend: The font extend property. 

951 

952 Returns: 

953 Nothing. 

954 

955 """ 

956 self.font_extend = font_extend 

957 

958 def set_theme(self, theme: int) -> None: 

959 """ 

960 Set the theme property. 

961 

962 Args: 

963 theme: Format theme. 

964 

965 Returns: 

966 Nothing. 

967 

968 """ 

969 self.theme = theme 

970 

971 def set_hyperlink(self, hyperlink: bool = True) -> None: 

972 """ 

973 Set the properties for the hyperlink style. 

974 

975 Args: 

976 hyperlink: Default is True, turns property on. 

977 

978 Returns: 

979 Nothing. 

980 

981 """ 

982 self.xf_id = 1 

983 self.set_underline(1) 

984 self.set_theme(10) 

985 self.hyperlink = hyperlink 

986 

987 def set_color_indexed(self, color_index: Literal[0, 1]) -> None: 

988 """ 

989 Set the color index property. Some fundamental format properties use an 

990 indexed color instead of a rbg or theme color. 

991 

992 Args: 

993 color_index: Generally 0 or 1. 

994 

995 Returns: 

996 Nothing. 

997 

998 """ 

999 self.color_indexed = color_index 

1000 

1001 def set_font_only(self, font_only: bool = True) -> None: 

1002 """ 

1003 Set property to indicate that the format is used for fonts only. 

1004 

1005 Args: 

1006 font_only: Default is True, turns property on. 

1007 

1008 Returns: 

1009 Nothing. 

1010 

1011 """ 

1012 self.font_only = font_only 

1013 

1014 # Compatibility methods. These versions of the method names were added in an 

1015 # initial version for compatibility testing with Excel::Writer::XLSX and 

1016 # leaked out into production code. They are deprecated and will be removed 

1017 # in a future after a suitable deprecation period. 

1018 def set_font(self, font_name: str) -> None: 

1019 """Deprecated: Use set_font_name() instead.""" 

1020 self.font_name = font_name 

1021 

1022 def set_size(self, font_size: int) -> None: 

1023 """Deprecated: Use set_font_size() instead.""" 

1024 self.font_size = font_size 

1025 

1026 def set_color(self, font_color: Union[Color, str]) -> None: 

1027 """Deprecated: Use set_font_color() instead.""" 

1028 self.font_color = Color._from_value(font_color) 

1029 

1030 ########################################################################### 

1031 # 

1032 # Private API. 

1033 # 

1034 ########################################################################### 

1035 

1036 def _get_align_properties(self): 

1037 # pylint: disable=too-many-boolean-expressions 

1038 # Return properties for an Style xf <alignment> sub-element. 

1039 changed = 0 

1040 align = [] 

1041 

1042 # Check if any alignment options in the format have been changed. 

1043 if ( 

1044 self.text_h_align 

1045 or self.text_v_align 

1046 or self.indent 

1047 or self.rotation 

1048 or self.text_wrap 

1049 or self.shrink 

1050 or self.reading_order 

1051 ): 

1052 changed = 1 

1053 else: 

1054 return changed, align 

1055 

1056 # Indent is only allowed for some alignment properties. If it is 

1057 # defined for any other alignment or no alignment has been set then 

1058 # default to left alignment. 

1059 if ( 

1060 self.indent 

1061 and self.text_h_align != 1 

1062 and self.text_h_align != 3 

1063 and self.text_h_align != 7 

1064 and self.text_v_align != 1 

1065 and self.text_v_align != 3 

1066 and self.text_v_align != 5 

1067 ): 

1068 self.text_h_align = 1 

1069 

1070 # Check for properties that are mutually exclusive. 

1071 if self.text_wrap: 

1072 self.shrink = 0 

1073 if self.text_h_align == 4: 

1074 self.shrink = 0 

1075 if self.text_h_align == 5: 

1076 self.shrink = 0 

1077 if self.text_h_align == 7: 

1078 self.shrink = 0 

1079 if self.text_h_align != 7: 

1080 self.just_distrib = 0 

1081 if self.indent: 

1082 self.just_distrib = 0 

1083 

1084 continuous = "centerContinuous" 

1085 

1086 if self.text_h_align == 1: 

1087 align.append(("horizontal", "left")) 

1088 if self.text_h_align == 2: 

1089 align.append(("horizontal", "center")) 

1090 if self.text_h_align == 3: 

1091 align.append(("horizontal", "right")) 

1092 if self.text_h_align == 4: 

1093 align.append(("horizontal", "fill")) 

1094 if self.text_h_align == 5: 

1095 align.append(("horizontal", "justify")) 

1096 if self.text_h_align == 6: 

1097 align.append(("horizontal", continuous)) 

1098 if self.text_h_align == 7: 

1099 align.append(("horizontal", "distributed")) 

1100 

1101 if self.just_distrib: 

1102 align.append(("justifyLastLine", 1)) 

1103 

1104 # Property 'vertical' => 'bottom' is a default. It sets applyAlignment 

1105 # without an alignment sub-element. 

1106 if self.text_v_align == 1: 

1107 align.append(("vertical", "top")) 

1108 if self.text_v_align == 2: 

1109 align.append(("vertical", "center")) 

1110 if self.text_v_align == 4: 

1111 align.append(("vertical", "justify")) 

1112 if self.text_v_align == 5: 

1113 align.append(("vertical", "distributed")) 

1114 

1115 if self.rotation: 

1116 align.append(("textRotation", self.rotation)) 

1117 if self.indent: 

1118 align.append(("indent", self.indent)) 

1119 

1120 if self.text_wrap: 

1121 align.append(("wrapText", 1)) 

1122 if self.shrink: 

1123 align.append(("shrinkToFit", 1)) 

1124 

1125 if self.reading_order == 1: 

1126 align.append(("readingOrder", 1)) 

1127 if self.reading_order == 2: 

1128 align.append(("readingOrder", 2)) 

1129 

1130 return changed, align 

1131 

1132 def _get_protection_properties(self): 

1133 # Return properties for an Excel XML <Protection> element. 

1134 attributes = [] 

1135 

1136 if not self.locked: 

1137 attributes.append(("locked", 0)) 

1138 if self.hidden: 

1139 attributes.append(("hidden", 1)) 

1140 

1141 return attributes 

1142 

1143 def _get_format_key(self): 

1144 # Returns a unique hash key for a format. Used by Workbook. 

1145 if self._format_key is None: 

1146 self._format_key = ":".join( 

1147 str(x) 

1148 for x in ( 

1149 self._get_font_key(), 

1150 self._get_border_key(), 

1151 self._get_fill_key(), 

1152 self._get_alignment_key(), 

1153 self.num_format, 

1154 self.locked, 

1155 self.checkbox, 

1156 self.quote_prefix, 

1157 self.hidden, 

1158 ) 

1159 ) 

1160 

1161 return self._format_key 

1162 

1163 def _get_font_key(self): 

1164 # Returns a unique hash key for a font. Used by Workbook. 

1165 key = ":".join( 

1166 str(x) 

1167 for x in ( 

1168 self.bold, 

1169 self.font_color, 

1170 self.font_charset, 

1171 self.font_family, 

1172 self.font_outline, 

1173 self.font_script, 

1174 self.font_shadow, 

1175 self.font_strikeout, 

1176 self.font_name, 

1177 self.italic, 

1178 self.font_size, 

1179 self.underline, 

1180 self.theme, 

1181 ) 

1182 ) 

1183 

1184 return key 

1185 

1186 def _get_border_key(self): 

1187 # Returns a unique hash key for a border style. Used by Workbook. 

1188 key = ":".join( 

1189 str(x) 

1190 for x in ( 

1191 self.bottom, 

1192 self.bottom_color, 

1193 self.diag_border, 

1194 self.diag_color, 

1195 self.diag_type, 

1196 self.left, 

1197 self.left_color, 

1198 self.right, 

1199 self.right_color, 

1200 self.top, 

1201 self.top_color, 

1202 ) 

1203 ) 

1204 

1205 return key 

1206 

1207 def _get_fill_key(self): 

1208 # Returns a unique hash key for a fill style. Used by Workbook. 

1209 key = ":".join(str(x) for x in (self.pattern, self.bg_color, self.fg_color)) 

1210 

1211 return key 

1212 

1213 def _get_alignment_key(self): 

1214 # Returns a unique hash key for alignment formats. 

1215 

1216 key = ":".join( 

1217 str(x) 

1218 for x in ( 

1219 self.text_h_align, 

1220 self.text_v_align, 

1221 self.indent, 

1222 self.rotation, 

1223 self.text_wrap, 

1224 self.shrink, 

1225 self.reading_order, 

1226 ) 

1227 ) 

1228 

1229 return key 

1230 

1231 def _get_xf_index(self): 

1232 # Returns the XF index number used by Excel to identify a format. 

1233 if self.xf_index is not None: 

1234 # Format already has an index number so return it. 

1235 return self.xf_index 

1236 

1237 # Format doesn't have an index number so assign one. 

1238 key = self._get_format_key() 

1239 

1240 if key in self.xf_format_indices: 

1241 # Format matches existing format with an index. 

1242 return self.xf_format_indices[key] 

1243 

1244 # New format requiring an index. Note. +1 since Excel 

1245 # has an implicit "General" format at index 0. 

1246 index = 1 + len(self.xf_format_indices) 

1247 self.xf_format_indices[key] = index 

1248 self.xf_index = index 

1249 return index 

1250 

1251 def _get_dxf_index(self): 

1252 # Returns the DXF index number used by Excel to identify a format. 

1253 if self.dxf_index is not None: 

1254 # Format already has an index number so return it. 

1255 return self.dxf_index 

1256 

1257 # Format doesn't have an index number so assign one. 

1258 key = self._get_format_key() 

1259 

1260 if key in self.dxf_format_indices: 

1261 # Format matches existing format with an index. 

1262 return self.dxf_format_indices[key] 

1263 

1264 # New format requiring an index. 

1265 index = len(self.dxf_format_indices) 

1266 self.dxf_format_indices[key] = index 

1267 self.dxf_index = index 

1268 return index 

1269 

1270 ########################################################################### 

1271 # 

1272 # XML methods. 

1273 # 

1274 ###########################################################################