Change styles for complete document

Hi we are trying to change style of document, there are few issues that are seen and need support for resolving the issues
we are using the below function to change the font name and font size

def change_styles(self, file_path):
        t0 = time.perf_counter()
        base = os.path.splitext(os.path.basename(file_path))[0].replace(" ", "_")
        out_dir = os.path.join("/test/",base)
        os.makedirs(out_dir, exist_ok=True)
        out_path = os.path.join(out_dir, f"{base}.docx")


        try:
            doc = aw.Document(file_path)

            # Define helper to change font of runs if matches criteria
            def change_font(run):
                try:
                    font_name = (run.font.name or "").strip().lower()
                    if font_name in ["arial", "times new roman"]:
                        size = float(run.font.size)
                        run.font.name = self.target_font_name
                        if isclose(size, 12.0, abs_tol=0.01):
                            run.font.size = 11.0
                except Exception as e:
			print(e)

            # Process all runs in document (deep)
            try:
                runs = doc.get_child_nodes(aw.NodeType.RUN, True)
                run_count = runs.count
                for i in range(run_count):
                    run = runs[i].as_run()
                    change_font(run)
            except Exception as e:
		print(e)

            # Process footnotes
            try:
                footnotes = doc.get_child_nodes(aw.NodeType.FOOTNOTE, True)
                footnote_count = footnotes.count
                for i in range(footnote_count):
                    footnote = footnotes[i].as_footnote()
                    para_count = footnote.paragraphs.count
                    for j in range(para_count):
                        para = footnote.paragraphs[j]
                        run_count = para.runs.count
                        for k in range(run_count):
                            change_font(para.runs[k])
            except Exception as e:
		print(e)

            # Process headers and footers
            try:
                section_count = doc.sections.count
                for s in range(section_count):
                    section = doc.sections[s]
                    hf_count = section.headers_footers.count if section.headers_footers is not None else 0
                    for h in range(hf_count):
                        hf = section.headers_footers[h]
                        if hf is not None:
                            para_count = hf.paragraphs.count
                            for p in range(para_count):
                                para = hf.paragraphs[p]
                                run_count = para.runs.count
                                for r in range(run_count):
                                    change_font(para.runs[r])
            except Exception as e:
		print(e)

            # Process shapes (which may contain text)
            try:
                shapes = doc.get_child_nodes(aw.NodeType.SHAPE, True)
                shape_count = shapes.count
                for i in range(shape_count):
                    shape = shapes[i].as_shape()

                    # Use get_text_frame() method to check for text
                    try:
                        text_frame = shape.get_text_frame()
                    except AttributeError:
                        text_frame = None

                    if text_frame is not None:
                        para_count = text_frame.paragraphs.count
                        for j in range(para_count):
                            para = text_frame.paragraphs[j]
                            run_count = para.runs.count
                            for k in range(run_count):
                                change_font(para.runs[k])
            except Exception as e:
		print(e)

            # Update document layout before saving
            try:
                doc.update_page_layout()
            except Exception as e:
		print(e)

            try:
                doc.save(out_path)
            except Exception as e:
                
                return out_path, e

            t1 = time.perf_counter()
            return out_path, "OK"

        except Exception as e:
		print(e)

issues are,

  1. when we open the saved file and enter new word/sentence the text is seen in either airal /times new roman

  2. the bullet points are not changing the font size/font name

  3. when the font size and name are changed if any flow charts are word wrapped their location are changing

can you please help in resolution using python?

@Prakruth

To address the issues you’re facing with changing the styles in your document, let’s break down each problem and provide clear solutions.

  1. New Text Appearing in Default Fonts: This issue typically arises when the default styles in the document are not updated. To ensure that new text uses the desired font, set the default font for the document. You can do this by accessing the default_font property of the StyleCollection and setting it to your target font. Here’s how you can do it:

    doc.styles.default_font.name = self.target_font_name
    doc.styles.default_font.size = 11.0  # Set the default size as needed
    
  2. Bullet Points Not Changing Font Size/Name: Bullet points are often controlled by the paragraph styles. Ensure that the styles applied to the bullet points are also updated. You can iterate through the styles and update the bullet point styles specifically. Here’s an example:

    for style in doc.styles:
        if style.type == aw.StyleType.PARAGRAPH and style.list_format.list:
            style.font.name = self.target_font_name
            style.font.size = 11.0  # Adjust as needed
    
  3. Flow Charts Changing Location: This issue may occur due to the way text wrapping is handled when changing font sizes. To prevent flow charts from moving, ensure that you are not altering the layout properties of the shapes. Check the TextFrame properties of the shapes and ensure they are set correctly after changing the font.

    If you are using shapes with text, set the text wrapping style explicitly:

    for shape in doc.get_child_nodes(aw.NodeType.SHAPE, True):
        text_frame = shape.get_text_frame()
        if text_frame:
            text_frame.text_wrap = True  # Ensure text wrapping is enabled
    

Next Steps:

  • Implement the above code snippets in your rebrand_document function.
  • Test the document after making these changes to confirm that the issues are resolved.
  • If problems persist, review the document’s styles to ensure that all relevant styles are being updated.

Please proceed with these steps, and let me know if you need further assistance or clarification!

@Prakruth Could you please attach your input document, your current and expected output documents? We will check the issue and provide you more information.
Is you goal simply change font name and size in the document?

schedule.docx (76.7 KB)

Please find the attached document, we are able to change style(font name from “Times New Roman” to “Aptos”) but the font name is not reflecting when the document is saved and re-opened.
Same is the case with numbering

Thank you for additional information. Please try using the following code to change font in the document:

def change_font(font) :
    font.name = "Aptos"
    font.size = 10
doc = aw.Document("C:\\Temp\\in.docx")

for n in doc.get_child_nodes(aw.NodeType.ANY, True):
    match n.node_type:
        case aw.NodeType.RUN:
            change_font(n.as_run().font)
        case aw.NodeType.PARAGRAPH:
            change_font(n.as_paragraph().paragraph_break_font)
        case aw.NodeType.FIELD_START:
            change_font(n.as_field_start().font)
        case aw.NodeType.FIELD_END:
            change_font(n.as_field_end().font)
        case aw.NodeType.FIELD_SEPARATOR:
            change_font(n.as_field_separator().font)
        case aw.NodeType.FOOTNOTE:
            change_font(n.as_footnote().font)
        case aw.NodeType.FORM_FIELD:
            change_font(n.as_form_field().font)
        case aw.NodeType.SPECIAL_CHAR:
            change_font(n.as_special_char().font)
    
doc.save("C:\\Temp\\out.docx")

thanks for quick response, but this code worked for me

   doc = aw.Document(input_path)
  #1) Retarget base styles so newly-typed text also uses the new font
    for style in doc.styles:
        if style.type in (aw.StyleType.PARAGRAPH, aw.StyleType.CHARACTER, aw.StyleType.TABLE):
            f = style.font
            f.name = font_name
            f.name_bi = font_name
            f.name_far_east = font_name


    # changes to styles
    for name in ("Normal", "Default Paragraph Font", "Heading 1", "Heading 2", "Heading 3"):
        st = doc.styles.get_by_name(name)
        if st is not None:
            f = st.font
            f.name = font_name
            f.name_bi = font_name
            f.name_far_east = font_name


    # 2) Ensure list numbers/bullets (labels) use the new font & size
    for i in range(doc.lists.count):
        lst = doc.lists[i]
        lvls = lst.list_levels
        for j in range(lvls.count):
            lf = lvls[j].font
            lf.name = font_name
            lf.name_bi = font_name
            lf.name_far_east = font_name


    # 3) Force-update every existing run (deep scan: body, headers/footers, shapes, notes, comments, etc.)
    runs = doc.get_child_nodes(aw.NodeType.RUN, True)  # True = deep
    for k in range(runs.count):
        r = runs[k].as_run()
        f = r.font
        f.name = font_name
        f.name_bi = font_name
        f.name_far_east = font_name


    # 4) Refresh dynamic content (e.g., TOC) so its display reflects style changes
    doc.update_fields()

@Prakruth Your code des almost the same as I have proposed. The only difference my code changes explicit formatting applied to the nodes in the document. You can replace the 3rd stage of your code with code I have proposed to make sure font is applied to whole document’s content.

follow up question on change of styles
when we are changing the font in text box in attached document say to “Aptose” like early, certain data in text box is getting hidden due to text box property, can we fix the dimensions according to text in text box without overlay?

@Prakruth You can try setting TextBox.fit_shape_to_text property to resolve this problem. but this might affect the layout.
Unfortunately, there is no easy way to fix this whiteout affecting the original shapes layout.

follow-up on this
Hi can you please help me with the following

  1. change the comment text font size to 8pt
  2. change the comment subject to size 10pt
  3. comment reference to 12pt
  4. highlight the footer table(top border) with blue color

@Prakruth Could you please attach your input and expected output documents here for our reference? This will help us to better understand your requirements. We will check your documents and provide you more information.

can you please help us if we can access comment subject, comment text fonts and comment references
attaching document for footer table border
file heading has sample content and desired output in heading_output

@Prakruth MS Word does not allow you to change the fonts for comment text and comment subject separately. The font size for balloons is stored in the “Balloon Text” style. Here is the code you need to use to make changes:

doc = aw.Document("headings.docx")

balloon_style = doc.styles.get_by_style_identifier(aw.StyleIdentifier.BALLOON_TEXT)
balloon_style.font.size = 8

comment = doc.get_child(aw.NodeType.COMMENT_RANGE_START, 0, True).as_comment_range_start()
comment_reference = comment.next_sibling.as_run()
comment_reference.font.size = 12

footer = doc.first_section.headers_footers.get_by_header_footer_type(aw.HeaderFooterType.FOOTER_PRIMARY)
table = footer.get_child(aw.NodeType.TABLE, 0, True).as_table()

table.set_border(aw.BorderType.TOP, aw.LineStyle.SINGLE, 1, aspose.pydrawing.Color.blue, True)

doc.save("output.docx")

thanks for the code, comments when opened in document are not seen with newer font.size as 12
though when printed as run.font.size is 12pt

@Prakruth I can also see changes in the document:

the comment text cannot be viewed with updated font size correct?

@Prakruth Could you please provide more information about the problem you have? If you are referring to comments in balloons, this is how comments are displayed in MS Word, and we cannot change it.

thanks for the update that we cannot change font styles for comments.
this is a follow-up for the footer table where are trying to add table border
while operating only on footer table is giving us good results but when we (referring to Headings.docx) footer details say footer center(page number to font size 11, and everything under footer section, including footer notes, end notes, and respective continuations to font size say “9”) border styles for tables are vanishing
is there a way to make changes to both table border and font size in single go?

@Prakruth Unfortunately, it is not quite clear what the problem is. The code provided by Vyacheslav does exactly what it required - changes font and specifies table border in the document footer.

headings.docx (83.3 KB)
headings_output.docx (80.4 KB)

Headings is the input file, while headings_output is what is desired,
while performing the font change operations independently, table border and font style changes are happening perfectly fine.

when we try to integrate both font style changes and border changes with text removal in sequence, the changes are not happening as desired