PHPackages                             phpoker/poker - PHPackages - PHPackages  [Skip to content](#main-content)[PHPackages](/)[Directory](/)[Categories](/categories)[Trending](/trending)[Leaderboard](/leaderboard)[Changelog](/changelog)[Analyze](/analyze)[Collections](/collections)[Log in](/login)[Sign up](/register)

1. [Directory](/)
2. /
3. [Utility &amp; Helpers](/categories/utility)
4. /
5. phpoker/poker

ActiveLibrary[Utility &amp; Helpers](/categories/utility)

phpoker/poker
=============

A comprehensive PHP library for working with Poker data and operations.

1.0.0(1y ago)214051MITPHPPHP ^8.2.0CI passing

Since Mar 6Pushed 3mo ago2 watchersCompare

[ Source](https://github.com/PHPoker/Poker)[ Packagist](https://packagist.org/packages/phpoker/poker)[ RSS](/packages/phpoker-poker/feed)WikiDiscussions main Synced 1mo ago

READMEChangelog (1)Dependencies (7)Versions (6)Used By (0)

 [![PHPoker](https://raw.githubusercontent.com/PHPoker/Poker/refs/heads/main/docs/logo-with-text.png)](https://raw.githubusercontent.com/PHPoker/Poker/refs/heads/main/docs/logo-with-text.png)

 [![GitHub Workflow Status (master)](https://github.com/PHPoker/Poker/actions/workflows/tests.yml/badge.svg)](https://github.com/PHPoker/Poker/actions) [![Total Downloads](https://camo.githubusercontent.com/270cd18229ae7ced5d4a5be999ede0b9f129290a7aa88f32a9cc0c7c6b1089b0/68747470733a2f2f696d672e736869656c64732e696f2f7061636b61676973742f64742f5048506f6b65722f706f6b6572)](https://packagist.org/packages/PHPoker/poker) [![Latest Version](https://camo.githubusercontent.com/e203158209cdb0b4a59d25d76c8921e215618f44c901e3b0d626fa5424e8fa32/68747470733a2f2f696d672e736869656c64732e696f2f7061636b61676973742f762f5048506f6b65722f706f6b6572)](https://packagist.org/packages/PHPoker/poker) [![License](https://camo.githubusercontent.com/785f4a35447148115a9e5ebe12006e476f7d1d5e3779183006d43a7be5742d34/68747470733a2f2f696d672e736869656c64732e696f2f6769746875622f6c6963656e73652f5048506f6b65722f706f6b6572)](https://packagist.org/packages/PHPoker/poker)

---

PHP's Premier Poker Solution

> **Requires [PHP 8.2+](https://php.net/releases/)**

### ⚡️ Installation using [Composer](https://getcomposer.org):

[](#️-installation-using-composer)

```
composer require phpoker/poker
```

### ✨ Features

[](#-features)

- Base classes for common card + poker related entities
    - Card
    - CardFace
    - CardSuit
    - CardCollection
- Evaluate
    - Highly optimized 5-card/7-card hand evaluators (port of Kevin "CactusKev" Suffecool's algorithm)

### Usage

[](#usage)

PHPoker provides a comprehensive toolkit for working with cards, decks, and poker hand evaluation. Below are examples of the main features and how to use them.

### Working with Cards

[](#working-with-cards)

#### Creating Cards

[](#creating-cards)

```
use PHPoker\Poker\Card;
use PHPoker\Poker\Enum\CardFace;
use PHPoker\Poker\Enum\CardSuit;

// Create a card using enums
$aceOfSpades = Card::make(CardFace::ACE, CardSuit::SPADE);

// Create a card from text notation
$kingOfHearts = Card::fromText('Kh'); // K = King, h = hearts
$queenOfClubs = Card::fromText('Q♣'); // Works with Unicode symbols too

// Create a random card
$randomCard = Card::random();
```

#### Card Properties and Methods

[](#card-properties-and-methods)

```
// Get card details
echo $aceOfSpades->face->name;  // "ACE"
echo $aceOfSpades->suit->name;  // "SPADE"

// Convert to string
echo $aceOfSpades->toString();       // "As" (default text format)
echo $aceOfSpades->toString(true);   // "A♠" (with Unicode suit symbol)

// Get HTML representation
echo $aceOfSpades->toHtml();         // "[ As ]"
echo $aceOfSpades->toHtml(true);     // "[ A♠ ]"

// Check card equality
$card1 = Card::fromText('Ah');
$card2 = Card::fromText('Ah');
$card3 = Card::fromText('As');

$card1->isEqualTo($card2); // true - same face and suit
$card1->isEqualTo($card3); // false - different suit
Card::areEqual($card1, $card2); // true - static method alternative
```

### Working with Card Enums

[](#working-with-card-enums)

#### Card Faces

[](#card-faces)

```
use PHPoker\Poker\Enum\CardFace;

// Accessing face values
CardFace::ACE->value;    // 12
CardFace::KING->value;   // 11
CardFace::QUEEN->value;  // 10
CardFace::JACK->value;   // 9
CardFace::TEN->value;    // 8
CardFace::TWO->value;    // 0

// Get symbol representation
CardFace::ACE->symbol();   // "A"
CardFace::KING->symbol();  // "K"
CardFace::TEN->symbol();   // "T"

// Get face value (numeric values for comparing cards)
CardFace::ACE->faceValue();     // 14 (Ace high by default)
CardFace::ACE->faceValue(true); // 1 (Ace low)
CardFace::KING->faceValue();    // 13
CardFace::TWO->faceValue();     // 2

// Parse from text
$face = CardFace::fromText('Q');  // CardFace::QUEEN
$face = CardFace::fromText('10'); // CardFace::TEN
$face = CardFace::fromText('t');  // CardFace::TEN (case-insensitive)
$face = CardFace::fromText('ace'); // CardFace::ACE (full name works too)

// Get all symbols
$symbols = CardFace::symbols(); // ['2', '3', '4', '5', '6', '7', '8', '9', 'T', 'J', 'Q', 'K', 'A']

// Increment a face
$face = CardFace::NINE;
$face->plus(1);  // CardFace::TEN
$face->plus(2);  // CardFace::JACK
```

#### Card Suits

[](#card-suits)

```
use PHPoker\Poker\Enum\CardSuit;

// Accessing suits
CardSuit::CLUB;     // Club enum
CardSuit::DIAMOND;  // Diamond enum
CardSuit::HEART;    // Heart enum
CardSuit::SPADE;    // Spade enum

// Get symbol representation
CardSuit::CLUB->symbol();    // "♣"
CardSuit::DIAMOND->symbol(); // "♦"
CardSuit::HEART->symbol();   // "♥"
CardSuit::SPADE->symbol();   // "♠"

// Get text representation (for short form notation)
CardSuit::CLUB->text();    // "c"
CardSuit::DIAMOND->text(); // "d"
CardSuit::HEART->text();   // "h"
CardSuit::SPADE->text();   // "s"

// Parse from text
$suit = CardSuit::fromText('c');    // CardSuit::CLUB
$suit = CardSuit::fromText('♦');    // CardSuit::DIAMOND
$suit = CardSuit::fromText('heart'); // CardSuit::HEART
$suit = CardSuit::fromText('SPADE'); // CardSuit::SPADE (case-insensitive)

// Get a random suit
$randomSuit = CardSuit::random();
```

### Working with Card Collections

[](#working-with-card-collections)

Card collections allow you to work with groups of cards like hands and decks.

#### Creating Collections

[](#creating-collections)

```
use PHPoker\Poker\Collections\CardCollection;
use PHPoker\Poker\Card;
use PHPoker\Poker\Enum\CardFace;
use PHPoker\Poker\Enum\CardSuit;

// Create a collection with individual cards
$hand = CardCollection::make([
    Card::make(CardFace::ACE, CardSuit::SPADE),
    Card::make(CardFace::ACE, CardSuit::HEART),
]);

// Create a collection from text notation
$hand = CardCollection::fromText('As Ah Kh Kd 2c');

// Create a collection from array of text
$hand = CardCollection::fromText(['As', 'Ah', 'Kh', 'Kd', '2c']);

// Create a deck (all 52 cards, shuffled)
$deck = CardCollection::createDeck();
```

#### Manipulating Collections

[](#manipulating-collections)

```
// Get unique cards (remove duplicates)
$uniqueCards = $hand->uniqueCards();

// Sort cards by face value
$sortedAscending = $hand->sortByFaceValue();
$sortedDescending = $hand->sortByFaceValueDesc();

// Get cards of a specific face
$aces = $hand->ofFace(CardFace::ACE);

// Get cards of a specific suit
$hearts = $hand->ofSuit(CardSuit::HEART);

// Discard specific cards
$remainingCards = $hand->discard('As Ah'); // By string notation
$remainingCards = $hand->discard(['As', 'Ah']); // By array
$remainingCards = $hand->discard($otherCollection); // By collection

// Check if a collection contains a card, face, or suit
$hasAce = $hand->holding(CardFace::ACE);          // Check for an ace
$hasHearts = $hand->holding(CardSuit::HEART);     // Check for hearts
$hasAceOfSpades = $hand->holding(Card::fromText('As')); // Check for specific card
```

### Collection Hand Evaluation

[](#collection-hand-evaluation)

The library includes a powerful hand evaluation engine based on Kevin "CactusKev" Suffecool's algorithm with perfect-hash improvements by Paul Senzee. This provides fast and accurate poker hand evaluation.

#### Evaluating a Hand

[](#evaluating-a-hand)

```
use PHPoker\Poker\Collections\CardCollection;

// Create a hand from text notation
$royalFlush = CardCollection::fromText('Ah Kh Qh Jh Th');
$fourOfAKind = CardCollection::fromText('Ah Ad As Ac Kh');
$twoPair = CardCollection::fromText('Ah Ad Kh Ks Qc');
$highCard = CardCollection::fromText('Ah Kd Qs Jc 9h');

// Get the hand rank as an enum
$handRank = $royalFlush->evaluate();
echo $handRank->name; // "STRAIGHT_FLUSH" (Royal Flush is a type of Straight Flush)

$handRank = $fourOfAKind->evaluate();
echo $handRank->name; // "FOUR_OF_A_KIND"

$handRank = $twoPair->evaluate();
echo $handRank->name; // "TWO_PAIR"

$handRank = $highCard->evaluate();
echo $handRank->name; // "HIGH_CARD"
```

#### Comparing Hands

[](#comparing-hands)

```
// Create two hands to compare
$royalFlush = CardCollection::fromText('Ah Kh Qh Jh Th');
$fourOfAKind = CardCollection::fromText('Ah Ad As Ac Kh');

// Get numerical ranks for each hand
$royalFlushRank = $royalFlush->rankHand();
$fourOfAKindRank = $fourOfAKind->rankHand();

// Compare the ranks (lower is better)
if ($royalFlushRank < $fourOfAKindRank) {
    echo "Royal Flush wins!";
} else {
    echo "Four of a Kind wins!";
}
// Output: "Royal Flush wins!"

// Another comparison
$fullHouse = CardCollection::fromText('Ah As Ad Kh Ks');
$flush = CardCollection::fromText('Ah Jh 8h 6h 2h');

if ($fullHouse->rankHand() < $flush->rankHand()) {
    echo "Full House wins!";
} else {
    echo "Flush wins!";
}
// Output: "Full House wins!"
```

#### Collection Analysis

[](#collection-analysis)

```
// Get collection of unique faces
$uniqueFaces = $hand->faces();

// Get collection of unique suits
$uniqueSuits = $hand->suits();

// Count suits in the collection
$suitCounts = $hand->countSuits(); // Returns Collection with counts

// Count faces in the collection
$faceCounts = $hand->countFaces(); // Returns Collection with counts

// Find the difference between two collections
$remainingCards = $hand->diffCards($cardsToRemove);
```

#### Collection Output

[](#collection-output)

```
// Convert to string (default space-separated)
echo $hand->toString();        // "As Ah Kh Kd 2c"

// Custom separator
echo $hand->toString(',');     // "As,Ah,Kh,Kd,2c"

// Convert to HTML
echo $hand->toHtml();          // HTML representation with colored suits

// Convert cards to their unique integer values
$cardIntegers = $hand->toIntegers();
```

### 🛠️ Development &amp; Contributing

[](#️-development--contributing)

All contributions are welcomed -- bug fixes, features, ideas, criticisms, optimizations!

Take advantage of the included development tools:

🧹 Keep a modern codebase with **Laravel Pint**:

```
composer lint
```

✅ Run refactors using **Rector**

```
composer refacto
```

⚗️ Run static analysis using **PHPStan**:

```
composer test:types
```

✅ Run unit tests using **PEST**

```
composer test:unit
```

🚀 Run the entire test suite:

```
composer test
```

**PHPoker** was created by **[Nick Poulos](https://nickpoulos.info)** under the **[MIT license](https://opensource.org/licenses/MIT)**.

###  Health Score

40

—

FairBetter than 88% of packages

Maintenance63

Regular maintenance activity

Popularity21

Limited adoption so far

Community9

Small or concentrated contributor base

Maturity54

Maturing project, gaining track record

 Bus Factor1

Top contributor holds 100% of commits — single point of failure

How is this calculated?**Maintenance (25%)** — Last commit recency, latest release date, and issue-to-star ratio. Uses a 2-year decay window.

**Popularity (30%)** — Total and monthly downloads, GitHub stars, and forks. Logarithmic scaling prevents top-heavy scores.

**Community (15%)** — Contributors, dependents, forks, watchers, and maintainers. Measures real ecosystem engagement.

**Maturity (30%)** — Project age, version count, PHP version support, and release stability.

###  Release Activity

Cadence

Unknown

Total

1

Last Release

438d ago

### Community

Maintainers

![](https://www.gravatar.com/avatar/86eb716fc596f9c96b4ff794d367dc827f2f5069de7d1dab74c3156411421a86?d=identicon)[nickpoulos](/maintainers/nickpoulos)

---

Top Contributors

[![nickpoulos](https://avatars.githubusercontent.com/u/3959529?v=4)](https://github.com/nickpoulos "nickpoulos (29 commits)")

---

Tags

phppokertexastexas hold emhold em

###  Code Quality

TestsPest

Static AnalysisPHPStan, Rector

Code StyleLaravel Pint

Type Coverage Yes

### Embed Badge

![Health badge](/badges/phpoker-poker/health.svg)

```
[![Health](https://phpackages.com/badges/phpoker-poker/health.svg)](https://phpackages.com/packages/phpoker-poker)
```

###  Alternatives

[stevebauman/location

Retrieve a user's location by their IP Address

1.3k7.6M65](/packages/stevebauman-location)[monicahq/laravel-cloudflare

Add Cloudflare ip addresses to trusted proxies for Laravel.

3372.7M4](/packages/monicahq-laravel-cloudflare)[kra8/laravel-snowflake

Snowflake for Laravel and Lumen.

188402.3k6](/packages/kra8-laravel-snowflake)[bezhansalleh/filament-google-analytics

Google Analytics integration for FilamentPHP

205144.8k5](/packages/bezhansalleh-filament-google-analytics)[laragear/preload

Effortlessly make a Preload script for your Laravel application.

119363.5k](/packages/laragear-preload)[napp/xray-laravel

AWS X-Ray for Laravel applications.

61407.3k](/packages/napp-xray-laravel)

PHPackages © 2026

[Directory](/)[Categories](/categories)[Trending](/trending)[Changelog](/changelog)[Analyze](/analyze)
