A simple, powerful, and cross-platform Python library for adding colors, styles, rich markup support, and beautiful tables to your terminal output. Optimized for Windows 10+, Linux, and macOS.
- β¨ Features
- π¦ Installation
- π Quick Start
- π¨ Color Reference
- π‘ Usage Examples
- π Table Module
- π Environment Variables
- π API Reference
- π Rich Markup Support
- π₯οΈ Platform Support
- π οΈ Development & Testing
- π― Best Practices
β οΈ Error Handling- π Performance
- π Quick Reference
- π€ Contributing
- π License
- π¨βπ» Author
- π₯οΈ Cross-platform support β Works on Windows, Linux, and macOS
- π― Windows 10+ optimized β Uses native ANSI processing on Windows Console
- π Rich color palette β 16 standard colors with light variants
- π Simple syntax β Full names, abbreviations, and combined formats
- π§ Flexible formatting β Foreground, background, and text attributes
- π Rich markup β Parse and render
[red]Error[/]or[bold white on red]CRITICAL[/] - π Table support β Create beautiful colored tables with Rich-style API
- π Lightweight β Zero external dependencies
- ποΈ Environment control β Enable/disable colors globally with env vars
- π‘ Error handling β Graceful fallbacks when unsupported colors are used
pip install make_colorsfrom make_colors import make_colors
# Simple colored text
print(make_colors("Hello World!", "red"))
# Text with background
print(make_colors("Important Message", "white", "red"))
# Using shortcuts
print(make_colors("Quick and easy", "r", "bl")) # red text, blue background
# Using underscore notation
print(make_colors("One-liner style", "green_yellow")) # green text on yellow background
# Rich markup
print(make_colors("[bold white on red] CRITICAL [/]"))
# Import all
from make_colors import *
print(bl("Im Blue"))
color = Colors('red', 'white')
print(color("White on Red"))
color = Color('white', 'red')
print(color("TEST"))
# Create beautiful tables
from make_colors.table import Table
table = Table(title="Server Status", title_style="bold cyan")
table.add_column("Service", style="bold")
table.add_column("Status", style="green")
table.add_column("Uptime", style="yellow")
table.add_row("Web Server", "β Running", "15d 6h")
table.add_row("Database", "β Running", "15d 6h")
table.add_row("Cache", "β Warning", "2d 3h", style="yellow")
print(table.draw())| Color Name | Shortcuts | Light Variant | Light Shortcut |
|---|---|---|---|
| black | b, bk | lightblack | lb |
| red | r, rd, re | lightred | lr |
| green | g, gr, ge | lightgreen | lg |
| yellow | y, ye, yl | lightyellow | ly |
| blue | bl | lightblue | lb |
| magenta | m, mg, ma | lightmagenta | lm |
| cyan | c, cy, cn | lightcyan | lc |
| white | w, wh, wi, wt | lightwhite | lw |
# Standard colors
print(make_colors("β Black text", "black"))
print(make_colors("β Red text", "red"))
print(make_colors("β Green text", "green"))
print(make_colors("β Yellow text", "yellow"))
print(make_colors("β Blue text", "blue"))
print(make_colors("β Magenta text", "magenta"))
print(make_colors("β Cyan text", "cyan"))
print(make_colors("β White text", "white"))
# Light variants
print(make_colors("β Light Red", "lightred"))
print(make_colors("β Light Green", "lightgreen"))
print(make_colors("β Light Blue", "lightblue"))
print(make_colors("β Light Yellow", "lightyellow"))print(make_colors("Full color names", "red", "white"))
print(make_colors("Using shortcuts", "r", "w"))
print(make_colors("Mixed notation", "red", "w"))# Using underscore separator
print(make_colors("Error occurred!", "red_white"))
print(make_colors("Success!", "green_black"))
print(make_colors("Warning!", "yellow_red"))
# Using dash separator
print(make_colors("Info message", "blue-white"))
print(make_colors("Debug info", "cyan-black"))
# Using comma separator
print(make_colors("Critical message", "white,blue"))
print(make_colors("Alert info", "w,r"))# System status display
def show_status(service, status):
if status == "running":
return make_colors(f"[β] {service}", "lightgreen", "black")
elif status == "stopped":
return make_colors(f"[β] {service}", "lightred", "black")
else:
return make_colors(f"[?] {service}", "lightyellow", "black")
print(show_status("Web Server", "running"))
print(show_status("Database", "stopped"))
print(show_status("Cache", "unknown"))
# Log level formatting
def log_message(level, message):
colors = {
"ERROR": ("lightwhite", "red"),
"WARNING": ("black", "yellow"),
"INFO": ("lightblue", "black"),
"DEBUG": ("lightgrey", "black")
}
fg, bg = colors.get(level, ("white", "black"))
return f"{make_colors(f' {level} ', fg, bg)} {message}"
print(log_message("ERROR", "Connection failed"))
print(log_message("WARNING", "Deprecated method used"))
print(log_message("INFO", "Server started successfully"))
print(log_message("DEBUG", "Variable value: 42"))print(make_colors("Bold text", "red", attrs=["bold"]))
print(make_colors("Underlined", "blue", attrs=["underline"]))
print(make_colors("Italic + Bold", "green", attrs=["italic", "bold"]))import time
for i in range(0, 101, 20):
bar = "β" * (i // 5) + "β" * (20 - i // 5)
print(f"\r{make_colors(f'[{bar}] {i}%', 'yellow')}", end="")
time.sleep(0.2)
print()
def progress_bar(current, total, width=50):
percentage = current / total
filled = int(width * percentage)
bar = "β" * filled + "β" * (width - filled)
if percentage < 0.5:
color = "red"
elif percentage < 0.8:
color = "yellow"
else:
color = "green"
return make_colors(f"[{bar}] {current}/{total} ({percentage:.1%})", color)
# Simulate progress
for i in range(0, 101, 10):
print(f"\r{progress_bar(i, 100)}", end="", flush=True)
time.sleep(0.1)
print() # New line after completiondef create_menu():
options = [
("1", "Start Application", "green"),
("2", "Settings", "yellow"),
("3", "Help", "blue"),
("4", "Exit", "red")
]
print(make_colors(" π― Main Menu ", "white", "blue"))
print()
for key, option, color in options:
print(f" {make_colors(key, 'white', color)} {option}")
print()
return input("Select option: ")
# Usage
choice = create_menu()Create beautiful, colored tables with a Rich-style API!
from make_colors.table import Table
# Rich-style API
table = Table(title="[bold cyan]Package Info[/]", header_style="bold white")
table.add_column("Package", style="bold")
table.add_column("Version", style="green")
table.add_column("Status", style="yellow")
table.add_row("numpy", "1.21.0", "β OK")
table.add_row("pandas", "1.3.0", "β Update", style="bold yellow")
table.add_row("requests", "2.26.0", "β OK")
print(table.draw())- β
Rich-style API -
add_column()andadd_row() - β Traditional API - Compatible with classic table libraries
- β
Rich markup support - Use
[color]text[/]in headers and cells - β Column styling - Set colors per column
- β Row styling - Set colors per row
- β Flexible alignment - Left, center, right alignment
- β Data type formatting - Auto-format numbers, floats, text
- β All make_colors formats - Abbreviations, full names, attributes
from make_colors.table import Table
# With title and styles
table = Table(
title="My Report",
title_style="bold cyan", # or "bold-cyan"
header_style="bold white", # or "bold-white"
max_width=80 # 0 for unlimited
)# Add columns with styling
table.add_column("Name", style="bold", align="l")
table.add_column("Price", style="green", align="r", dtype="f")
table.add_column("Stock", style="cyan", align="r", dtype="i")
table.add_column("Status", style="yellow", align="c")
# Add rows with optional styling
table.add_row("Product A", 99.99, 150, "Available")
table.add_row("Product B", 149.99, 0, "Out of Stock", style="bold red")
table.add_row("Product C", 199.99, 75, "Low Stock", style="yellow")# Set column properties
table.set_cols_align(["l", "r", "r", "c"])
table.set_cols_valign(["t", "m", "b", "t"])
table.set_cols_dtype(["t", "f", "i", "t"])
table.set_cols_width([20, 10, 10, 15])
# Set column colors (NEW!)
table.set_cols_color(["bold", "green", "cyan", "yellow"])
table.set_cols_color(["y", "r", "c", "g"]) # Using abbreviations
# Set row colors (NEW!)
table.set_rows_color(["green", "yellow", "bold-red", None])
# Set header
table.header(["Name", "Price", "Stock", "Status"])
# Add rows
table.add_row("Product A", 99.99, 150, "Available")
table.add_row("Product B", 149.99, 0, "Out of Stock")Tables support Rich markup in headers, cells, and titles:
# Rich markup in title
table = Table(title="[bold cyan]Server Status[/]")
# Rich markup in column headers
table.add_column("[bold white]Service[/]")
table.add_column("[white on blue]Status[/]")
table.add_column("[white on green]Uptime[/]")
# Rich markup in cells
table.add_row("[bold]Web Server[/]", "β Running", "15d 6h")from make_colors.table import Table
table = Table(title="Package Version Checker", title_style="bold cyan")
table.add_column("Package", style="bold")
table.add_column("Installed", style="cyan")
table.add_column("Required", style="magenta")
table.add_column("Status", style="yellow")
table.add_row("numpy", "1.21.0", "1.20.0", "β OK")
table.add_row("pandas", "1.3.0", "1.4.0", "β Update", style="bold yellow")
table.add_row("requests", "2.26.0", "2.26.0", "β OK")
table.add_row("flask", "1.1.0", "2.0.0", "β Old", style="bold red")
print(table.draw())table = Table()
table.set_cols_align(["l", "c", "r", "r"])
table.set_cols_color(["bold-white", "cyan", "yellow", "magenta"])
table.header(["Service", "Status", "CPU %", "Memory %"])
table.add_row("Web Server", "β Running", "45.2", "62.8")
table.add_row("Database", "β Running", "78.5", "85.3")
table.add_row("Cache", "β Warning", "92.1", "95.7")
print(table.draw())table = Table(title="Task Status", title_style="bold-cyan")
table.header(["Task", "Status", "Progress", "Priority"])
table.add_row("Deploy to Production", "β Complete", "100%", "High")
table.add_row("Code Review", "β In Progress", "75%", "Medium")
table.add_row("Write Tests", "β Pending", "0%", "High")
table.add_row("Fix Bug #123", "β Blocked", "30%", "Critical")
# Color rows based on status
table.set_rows_color([
"bold-green", # Complete
"bold-yellow", # In Progress
"dim", # Pending
"bold-red" # Blocked
])
print(table.draw())table = Table(title="[bold magenta]Sales Dashboard[/]")
table.add_column("[bold white]Product[/]", align="l")
table.add_column("[bold green]Revenue[/]", align="r", dtype="f")
table.add_column("[white on blue]Units Sold[/]", align="r", dtype="i")
table.add_column("[bold yellow on black]Trend[/]", align="c")
table.add_row("Widget A", 125000.50, 1234, "π Up")
table.add_row("Widget B", 89000.25, 890, "π Down", style="dim")
table.add_row("Widget C", 250000.00, 2500, "π₯ Hot", style="bold-green")
print(table.draw())table = Table(title="User List", title_style="bold-cyan")
table.header(["ID", "Username", "Email", "Status"])
users = [
["001", "john_doe", "john@example.com", "Active"],
["002", "jane_smith", "jane@example.com", "Active"],
["003", "bob_wilson", "bob@example.com", "Inactive"],
["004", "alice_brown", "alice@example.com", "Active"],
["005", "charlie_davis", "charlie@example.com", "Active"],
]
for user in users:
table.add_row(*user)
# Alternate between dim and normal
table.set_rows_color(["dim", None, "dim", None, "dim"])
print(table.draw())# Horizontal: "l" (left), "c" (center), "r" (right)
table.set_cols_align(["l", "c", "r"])
# Vertical: "t" (top), "m" (middle), "b" (bottom)
table.set_cols_valign(["t", "m", "b"])# "a" (auto), "t" (text), "f" (float), "e" (exponential), "i" (integer)
table.set_cols_dtype(["t", "f", "i", "a"])# Customize border characters
table.set_chars(['-', '|', '+', '=']) # [horiz, vert, corner, header]
# Control decorations
table.set_deco(Table.BORDER | Table.HEADER) # Border + header line only
table.set_deco(Table.VLINES | Table.HLINES) # Only lines, no borderAll make_colors formats are supported:
# Full names
table.set_cols_color(["red", "green", "blue"])
# Abbreviations
table.set_cols_color(["r", "g", "bl"])
# With attributes
table.set_cols_color(["bold-red", "italic-cyan", "dim-yellow"])
# With background
table.set_cols_color(["white-red", "black-yellow", "green-black"])
# Mixed formats
table.set_cols_color(["bold-white", "r", "italic-cyan", "lb-b"])| Variable | Values | Description |
|---|---|---|
MAKE_COLORS |
0 or 1 |
Disable/enable colors globally |
MAKE_COLORS_FORCE |
0, 1, True |
Force colors even when unsupported |
MAKE_COLORS_DEBUG |
1, true, True |
Enable debug parsing logs |
Example:
import os
# Disable colors
os.environ['MAKE_COLORS'] = '0'
print(make_colors("No colors", "red")) # Output: "No colors" (no coloring)
# Force colors (useful for CI/CD or redirected output)
os.environ['MAKE_COLORS_FORCE'] = '1'
print(make_colors("Forced colors", "green")) # Always coloredMain function to colorize strings with ANSI or Rich markup.
string(str) β Input text, supports Rich markup like[red]Error[/]foreground(str) β Foreground colorbackground(str|None) β Background colorattrs(list) β List of attributes:bold,underline,italic, etc.force(bool) β Force enable colors
Returns:
str(Colorized string with ANSI escape codes)
Alias for make_colors.
Convenience print wrapper that applies make_colors before printing.
Parses strings like [bold red on black]Hello[/] into (content, fg, bg, style) tuples. Supports multiple tags.
Parses combined formats like red-yellow, g_b, expanding into (fg, bg).
Maps abbreviations like r, bl, lg to full names.
Examples:
# Basic usage
make_colors("Hello", "red")
# With background
make_colors("Hello", "white", "red")
# Using shortcuts
make_colors("Hello", "w", "r")
# Separator notation
make_colors("Hello", "white_red")
# Force colors
make_colors("Hello", "red", force=True)colored(string, fg, bg, attrs)β low-level ANSI outputrich_colored(string, color, bg, style)β Rich style supportsupports_color()β Detect terminal support, return:bool: True if colors are supported, False otherwise
from make_colors import MakeColors
if MakeColors.supports_color():
print("Colors are supported!")
else:
print("Colors not supported on this terminal")MakeColorsErrorβ Raised when invalid colors are usedMakeColorsWarningβ Non-critical fallback warnings
The library supports Rich-style markup similar to the rich package:
print(make_colors("[red]Error[/] [bold white on blue]CRITICAL[/] [green]OK[/]"))Supported styles:
- bold, italic, underline, dim, blink, reverse, strikethrough
# Using console
from make_colors import Console
console = Console()
console.print("[white on red]This is Example ERROR ![/]")- Windows 10+ β (full ANSI support)
- Older Windows
β οΈ requires ANSICON - Windows Terminal: π Excellent support with all features
- Most terminals: β Full support (xterm, gnome-terminal, konsole, etc.), almost all terminals supported
- Tmux/Screen: β Supported
- SSH sessions: β Supported when terminal supports colors
- Terminal.app: β Full support
- iTerm2: β Excellent support
- Other terminals: β Generally well supported
def test_all_colors():
"""Test all available colors"""
colors = ['black', 'red', 'green', 'yellow', 'blue', 'magenta', 'cyan', 'white']
light_colors = [f'light{color}' for color in colors if color != 'black'] + ['lightgrey']
print("=== Standard Colors ===")
for color in colors:
print(make_colors(f" {color.ljust(10)}", color, "black"))
print("\n=== Light Colors ===")
for color in light_colors:
print(make_colors(f" {color.ljust(15)}", color, "black"))
# Run the test
test_all_colors()from make_colors import MakeColors
print("Supports colors:", MakeColors.supports_color())def test_all_colors():
"""Test all available colors"""
colors = ['black', 'red', 'green', 'yellow', 'blue', 'magenta', 'cyan', 'white']
light_colors = [f'light{color}' for color in colors if color != 'black'] + ['lightgrey']
print("=== Standard Colors ===")
for color in colors:
print(make_colors(f" {color.ljust(10)}", color, "black"))
print("\n=== Light Colors ===")
for color in light_colors:
print(make_colors(f" {color.ljust(15)}", color, "black"))
# Run the test
test_all_colors()
### Testing Tables
```python
from make_colors.table import Table
# Test basic table
table = Table()
table.header(["Column 1", "Column 2", "Column 3"])
table.add_row("Data 1", "Data 2", "Data 3")
print(table.draw())
# Test colored table
table = Table(title="Test Table", title_style="bold cyan")
table.add_column("Name", style="bold")
table.add_column("Value", style="green")
table.add_row("Test", "Success", style="green")
print(table.draw())- Always check color support
MakeColors.supports_color()before production use - Provide fallbacks for environments without color support (e.g. plain text when disabled)
- Use env vars for CI/CD or logging
- Choose contrasting colors for better readability
- Test on multiple OSes/terminals/platforms to ensure compatibility
- Use tables for structured data - Tables make data more readable and professional
from make_colors import make_colors, MakeColors
def safe_print(text, fg="white", bg=None):
"""Safely print colored text with fallback"""
if MakeColors.supports_color():
print(make_colors(text, fg, bg))
else:
print(f"[{fg.upper()}] {text}")
# Usage
safe_print("This works everywhere!", "green")from make_colors import *
print(red("Error!"))
print(bl("Im Blue"))
print(green_on_black("Success"))
# Abbreviation
print(w_bl("White on Blue")) # white on blue
print(r_w("Red on White")) # red on white
print(g_b("Green on Black")) # green on black
print(lb_b("Light Blue on Black"))
color = Colors('red', 'white')
print(color("White on Red"))
color = Color('white', 'red')
print(color("TEST"))
# Try and see what happened π π- Invalid color β falls back to white on black
- Unknown attribute β ignored silently
- Raise
MakeColorsErrorfor invalid color names (if strict) - Raise
MakeColorsWarningfor warnings
try:
print(make_colors("Oops", "notacolor"))
except Exception as e:
print("Handled:", e)- Traditional call: ~0.00001s per render
- Rich markup parsing: slightly slower (~+10β15%)
- Table rendering: Optimized for large datasets
- Suitable for high-frequency logging and data visualization
- β
Single color:
[red]text[/] - β
With background:
[white on red]text[/] - β
With style:
[bold green]text[/] - β
Combined:
[bold white on red]ALERT[/] - β
Multiple tags:
[cyan]Info[/] [red]Error[/]
- β
Rich-style:
table.add_column("Name", style="bold") - β
Rich markup:
table.add_column("[white on blue]Status[/]") - β
Column colors:
table.set_cols_color(["r", "g", "b"]) - β
Row colors:
table.set_rows_color(["green", "yellow", "red"]) - β
Styling rows:
table.add_row(..., style="bold red")
PRs welcome! Open issues for feature requests or bugs. Contributions are welcome! Please feel free to submit a Pull Request. For major changes, please open an issue first to discuss what you would like to change.
Licensed under the MIT License. See LICENSE.
Hadi Cahyadi π§ cumulus13@gmail.com
β¨ Made with β€οΈ by Hadi Cahyadi for colorful terminal experiences!

