""" Unit tests for abstract block elements. Tests the core abstract block classes that form the foundation of the document model. """ import unittest from pyWebLayout.abstract.block import ( Block, BlockType, Paragraph, Heading, HeadingLevel, Quote, CodeBlock, HList, ListStyle, ListItem, Table, TableRow, TableCell, HorizontalRule, Image ) from pyWebLayout.abstract.inline import Word, LineBreak from pyWebLayout.style import Font class TestBlockElements(unittest.TestCase): """Test cases for basic block elements.""" def test_paragraph_creation(self): """Test creating and using paragraphs.""" paragraph = Paragraph() self.assertEqual(paragraph.block_type, BlockType.PARAGRAPH) self.assertEqual(paragraph.word_count, 0) self.assertIsNone(paragraph.parent) # Add words font = Font() word1 = Word("Hello", font) word2 = Word("World", font) paragraph.add_word(word1) paragraph.add_word(word2) self.assertEqual(paragraph.word_count, 2) # Test word iteration words = list(paragraph.words()) self.assertEqual(len(words), 2) self.assertEqual(words[0][1].text, "Hello") self.assertEqual(words[1][1].text, "World") def test_heading_levels(self): """Test heading creation with different levels.""" h1 = Heading(HeadingLevel.H1) h3 = Heading(HeadingLevel.H3) h6 = Heading(HeadingLevel.H6) self.assertEqual(h1.level, HeadingLevel.H1) self.assertEqual(h3.level, HeadingLevel.H3) self.assertEqual(h6.level, HeadingLevel.H6) self.assertEqual(h1.block_type, BlockType.HEADING) # Test level modification h1.level = HeadingLevel.H2 self.assertEqual(h1.level, HeadingLevel.H2) def test_quote_nesting(self): """Test blockquote with nested content.""" quote = Quote() # Add nested paragraphs p1 = Paragraph() p2 = Paragraph() quote.add_block(p1) quote.add_block(p2) self.assertEqual(p1.parent, quote) self.assertEqual(p2.parent, quote) # Test block iteration blocks = list(quote.blocks()) self.assertEqual(len(blocks), 2) self.assertEqual(blocks[0], p1) self.assertEqual(blocks[1], p2) def test_code_block(self): """Test code block functionality.""" code = CodeBlock("python") self.assertEqual(code.language, "python") self.assertEqual(code.line_count, 0) # Add code lines code.add_line("def hello():") code.add_line(" print('Hello!')") self.assertEqual(code.line_count, 2) # Test line iteration lines = list(code.lines()) self.assertEqual(len(lines), 2) self.assertEqual(lines[0][1], "def hello():") self.assertEqual(lines[1][1], " print('Hello!')") # Test language modification code.language = "javascript" self.assertEqual(code.language, "javascript") def test_list_creation(self): """Test list creation and item management.""" # Unordered list ul = HList(ListStyle.UNORDERED) self.assertEqual(ul.style, ListStyle.UNORDERED) self.assertEqual(ul.item_count, 0) # Add list items item1 = ListItem() item2 = ListItem() ul.add_item(item1) ul.add_item(item2) self.assertEqual(ul.item_count, 2) self.assertEqual(item1.parent, ul) self.assertEqual(item2.parent, ul) # Test item iteration items = list(ul.items()) self.assertEqual(len(items), 2) # Test list style change ul.style = ListStyle.ORDERED self.assertEqual(ul.style, ListStyle.ORDERED) def test_definition_list(self): """Test definition list with terms.""" dl = HList(ListStyle.DEFINITION) # Add definition items with terms dt1 = ListItem(term="Python") dt2 = ListItem(term="JavaScript") dl.add_item(dt1) dl.add_item(dt2) self.assertEqual(dt1.term, "Python") self.assertEqual(dt2.term, "JavaScript") # Test term modification dt1.term = "Python 3" self.assertEqual(dt1.term, "Python 3") def test_table_structure(self): """Test table, row, and cell structure.""" table = Table(caption="Test Table") self.assertEqual(table.caption, "Test Table") self.assertEqual(table.row_count["total"], 0) # Create rows and cells header_row = TableRow() data_row = TableRow() # Header cells h1 = TableCell(is_header=True) h2 = TableCell(is_header=True) header_row.add_cell(h1) header_row.add_cell(h2) # Data cells d1 = TableCell(is_header=False) d2 = TableCell(is_header=False, colspan=2) data_row.add_cell(d1) data_row.add_cell(d2) # Add rows to table table.add_row(header_row, "header") table.add_row(data_row, "body") # Test structure self.assertEqual(table.row_count["header"], 1) self.assertEqual(table.row_count["body"], 1) self.assertEqual(table.row_count["total"], 2) # Test cell properties self.assertTrue(h1.is_header) self.assertFalse(d1.is_header) self.assertEqual(d2.colspan, 2) self.assertEqual(d2.rowspan, 1) # Default # Test row cell count self.assertEqual(header_row.cell_count, 2) self.assertEqual(data_row.cell_count, 2) def test_table_sections(self): """Test table header, body, and footer sections.""" table = Table() # Add rows to different sections header = TableRow() body1 = TableRow() body2 = TableRow() footer = TableRow() table.add_row(header, "header") table.add_row(body1, "body") table.add_row(body2, "body") table.add_row(footer, "footer") # Test section iteration header_rows = list(table.header_rows()) body_rows = list(table.body_rows()) footer_rows = list(table.footer_rows()) self.assertEqual(len(header_rows), 1) self.assertEqual(len(body_rows), 2) self.assertEqual(len(footer_rows), 1) # Test all_rows iteration all_rows = list(table.all_rows()) self.assertEqual(len(all_rows), 4) # Check section labels sections = [section for section, row in all_rows] self.assertEqual(sections, ["header", "body", "body", "footer"]) def test_image_loading(self): """Test image element properties.""" # Test with basic properties img = Image("test.jpg", "Test image", 100, 200) self.assertEqual(img.source, "test.jpg") self.assertEqual(img.alt_text, "Test image") self.assertEqual(img.width, 100) self.assertEqual(img.height, 200) # Test property modification img.source = "new.png" img.alt_text = "New image" img.width = 150 img.height = 300 self.assertEqual(img.source, "new.png") self.assertEqual(img.alt_text, "New image") self.assertEqual(img.width, 150) self.assertEqual(img.height, 300) # Test dimensions tuple self.assertEqual(img.get_dimensions(), (150, 300)) def test_aspect_ratio_calculation(self): """Test image aspect ratio calculations.""" # Test with specified dimensions img = Image("test.jpg", width=400, height=200) self.assertEqual(img.get_aspect_ratio(), 2.0) # 400/200 # Test with only one dimension img2 = Image("test.jpg", width=300) self.assertIsNone(img2.get_aspect_ratio()) # No height specified # Test scaled dimensions scaled = img.calculate_scaled_dimensions(max_width=200, max_height=150) # Should scale down proportionally self.assertEqual(scaled[0], 200) # Width limited by max_width self.assertEqual(scaled[1], 100) # Height scaled proportionally def test_simple_elements(self): """Test simple block elements.""" hr = HorizontalRule() br = LineBreak() self.assertEqual(hr.block_type, BlockType.HORIZONTAL_RULE) self.assertEqual(br.block_type, BlockType.LINE_BREAK) # These elements have no additional properties self.assertIsNone(hr.parent) self.assertIsNone(br.parent) if __name__ == '__main__': unittest.main()