{"id":27598068,"url":"https://github.com/noyzys/bukkit-region","last_synced_at":"2026-04-22T23:36:01.133Z","repository":{"id":288947692,"uuid":"969630280","full_name":"noyzys/bukkit-region","owner":"noyzys","description":"A flexible and extensible region internal api for Spigot/Bukkit,","archived":false,"fork":false,"pushed_at":"2025-05-23T12:56:27.000Z","size":24,"stargazers_count":1,"open_issues_count":1,"forks_count":0,"subscribers_count":1,"default_branch":"main","last_synced_at":"2025-06-21T06:34:42.747Z","etag":null,"topics":["api","bukkit","bukkit-api","bukkit-plugin","java","location","region-api","spigot","spigot-api"],"latest_commit_sha":null,"homepage":"","language":"Java","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/noyzys.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE.txt","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null}},"created_at":"2025-04-20T15:34:07.000Z","updated_at":"2025-05-23T12:56:30.000Z","dependencies_parsed_at":"2025-04-22T14:10:29.132Z","dependency_job_id":"3a7af0d6-7797-4dd7-911c-c6cdf586db7b","html_url":"https://github.com/noyzys/bukkit-region","commit_stats":null,"previous_names":["noyzys/bukkit-region"],"tags_count":0,"template":false,"template_full_name":null,"purl":"pkg:github/noyzys/bukkit-region","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/noyzys%2Fbukkit-region","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/noyzys%2Fbukkit-region/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/noyzys%2Fbukkit-region/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/noyzys%2Fbukkit-region/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/noyzys","download_url":"https://codeload.github.com/noyzys/bukkit-region/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/noyzys%2Fbukkit-region/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":32159959,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-04-22T17:06:48.269Z","status":"ssl_error","status_checked_at":"2026-04-22T17:06:19.037Z","response_time":58,"last_error":"SSL_connect returned=1 errno=0 peeraddr=140.82.121.5:443 state=error: unexpected eof while reading","robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":false,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["api","bukkit","bukkit-api","bukkit-plugin","java","location","region-api","spigot","spigot-api"],"created_at":"2025-04-22T14:10:25.882Z","updated_at":"2026-04-22T23:36:01.118Z","avatar_url":"https://github.com/noyzys.png","language":"Java","funding_links":[],"categories":[],"sub_categories":[],"readme":"                                                # nautchkafe-region \n\n## Features:\n- QuadTree implementation\n- Multiple region shapes (circle, square, rectangle)\n- Immutable region operations\n- Location-based checks\n- Visualizations internal api\n- Region transformations\n- Iteration over region points\n- Edge Detection\n\n## Example:\n\n```java\n// Selector shape:\nRegion region = RegionFactorySelector.createRegion(\n    \"circle\",\n    RegionLocation.fromBukkit(player.getLocation()),\n    10.0\n);\n\n// rectangle 10x20\nRegion rectangle = RegionFactorySelector.createRegion(\n    \"rectangle\", \n    centerLoc, \n    10.0, 20.0\n);\n\n// square \nRegion square = RegionFactorySelector.createRegion(\n    \"square\", \n    centerLoc, \n    15.0\n);\n\n// Manual creator:\nRegionLocation min = new RegionLocation(\"world\", 0, 64, 0);\nRegionLocation max = new RegionLocation(\"world\", 10, 64, 10);\n\nRegion customRegion = RegionSpawner.of(min, max,\n    (x, z) -\u003e x \u003e= min.x() \u0026\u0026 x \u003c= max.x() \u0026\u0026 z \u003e= min.z() \u0026\u0026 z \u003c= max.z()\n);\n\ndouble radius = 10.0;\nRegionLocation center = new RegionLocation(\"world\", 0, 64, 0);\nRegionLocation circleMin = new RegionLocation(\"world\", center.x() - radius, center.y(), center.z() - radius);\nRegionLocation circleMax = new RegionLocation(\"world\", center.x() + radius, center.y(), center.z() + radius);\n\nRegion circleRegion = RegionSpawner.of(circleMin, circleMax,\n    (x, z) -\u003e Math.pow(x - center.x(), 2) + Math.pow(z - center.z(), 2) \u003c= Math.pow(radius, 2)\n); \n// ...\n\n```\n\n## Visualization border material \n```java\nRegion spawnRegion = createCircularRegion.apply(player.getLocation());\nvisualize.accept(\n    spawnRegion,\n    player,\n    Material.GLOWSTONE, // block vizualization\n    200 // refresh time\n);\n\nRegion customRegion = RegionFactorySelector.createRegion(\n    \"rectangle\",\n    centerLoc,\n    20.0, 30.0\n);\n\nRegionVisualizer.visualize.accept(\n    customRegion,\n    player,\n    Material.DIAMOND_BLOCK,\n    100\n);\n```\n- TIP for performance:\n- Spatial Partitioning - QuadTree, Rtree, Octree (2d grid) ....\n- cache BlockData,\n- Batch processing, \n- Async render \n\n## Region#contains :: Checking Location Containment\n```java\nPlayer player = event.getPlayer();\nRegionLocation playerLoc = RegionLocation.fromBukkit(player.getLocation());\n\nif (circle.contains(playerLoc)) {\n    player.sendMessage(\"You're inside the circle region!\");\n}\n```\n\n```java\nboolean isInside = region.contains(RegionLocation.fromBukkit(player.getLocation()));\n```\n## Explanation:\n- region.contains(...): This checks if the location provided is within the boundaries of the region.\n\n## Region#applyToBounds :: Region Transformations\n```java\n// Scale region by 20%\nRegion scaled = circle.applyToBounds(x -\u003e x * 1.2);\n\n// Move region 5 blocks east\nRegion moved = circle.applyToBounds(x -\u003e x + 5);\n```\n\n## Explanation:\n- region.applyToBounds(...): This method creates a new Region where the bounds (min and max coordinates) have been modified according to the provided function.\n- x -\u003e x + 5.0: This is the function that adds 5.0 to every coordinate (x, y, z), effectively shifting the region by 5 units in each direction.\n**The result is a new Region (movedRegion) with the adjusted boundaries.**\n\n## Iterating Through Region Points\n```java\n// Get all locations in region with 1-block step\nList\u003cRegionLocation\u003e allPoints = circle.forEachInRegion(1.0);\n\n// Visualize region with particles\ncircle.forEachInRegion(0.5).forEach(loc -\u003e {\n    player.spawnParticle(\n        Particle.REDSTONE, \n        loc.toBukkit(), \n        1, \n        new Particle.DustOptions(Color.RED, 1)\n    );\n});\n```\n\n## Region#center Getting Region Center\n```java\nRegionLocation center = circle.center();\nplayer.teleport(center.toBukkit());\n```\n\n## Practical use case:\n```java\n@EventHandler\nvoid onPlayerMove(PlayerMoveEvent event) {\n    RegionLocation spawn = new RegionLocation(\"world\", 0, 64, 0);\n    Region spawnRegion = RegionFactorySelector.createRegion(\"square\", spawn, 50.0);\n    \n    if (spawnRegion.contains(RegionLocation.fromBukkit(event.getTo()))) {\n        event.getPlayer().sendMessage(\"Welcome to spawn area!\");\n    }\n}\n```\n\n## Example for block change place block:\n\n```java\n    Function\u003cRegionLocation, Region\u003e createSpawn = center -\u003e \n        RegionFactorySelector.createRegion(\"circle\", center, 15.0);\n    \n    BiPredicate\u003cRegion, RegionLocation\u003e isBorder = (region, loc) -\u003e \n        !region.contains(new RegionLocation(loc.world(), loc.x() + 1, loc.y(), loc.z())) ||\n        !region.contains(new RegionLocation(loc.world(), loc.x() - 1, loc.y(), loc.z())) ||\n        !region.contains(new RegionLocation(loc.world(), loc.x(), loc.y(), loc.z() + 1)) ||\n        !region.contains(new RegionLocation(loc.world(), loc.x(), loc.y(), loc.z() - 1));\n    \n    UnaryOperator\u003cRegionLocation\u003e withYOffset = loc -\u003e \n        new RegionLocation(loc.world(), loc.x(), loc.y() + 0.5, loc.z());\n    \n    BiConsumer\u003cRegion, Player\u003e visualize = (region, player) -\u003e {\n        Consumer\u003cRegionLocation\u003e showBorder = loc -\u003e \n            player.sendBlockChange(\n                withYOffset.apply(loc).toBukkit(),\n                Material.RED_STAINED_GLASS.createBlockData()\n            );\n        \n        region.forEachInRegion(1.0)\n            .stream()\n            .filter(loc -\u003e isBorder.test(region, loc))\n            .forEach(showBorder);\n    };\n    \n    BiFunction\u003cRegion, Player, Runnable\u003e scheduleCleanup = (region, player) -\u003e \n        () -\u003e region.forEachInRegion(1.0).stream()\n            .map(withYOffset)\n            .forEach(loc -\u003e \n                player.sendBlockChange(\n                    loc.toBukkit(), \n                    loc.toBukkit().getBlock().getBlockData()\n                )\n            );\n```\n\n```java\nEventHandler\nvoid onPlayerInteract(PlayerInteractEvent event) {\n    renderer.render(event.getPlayer(), Particle.END_ROD);\n}\n\n// Optimized rendering version (checks distance/chunk loading)\nfinal class RegionRenderer {\n    private final Region region;\n    private final double step;\n\n    RegionRenderer(Region region, double step) {\n        this.region = region;\n        this.step = step;\n    }\n\n    void render(Player player, Particle particle) {\n        Chunk playerChunk = player.getLocation().getChunk();\n        String world = region.center().world();\n\n        region.forEachInRegion(step).forEach(loc -\u003e {\n            Location bukkitLoc = loc.toBukkit();\n            \n            if (!bukkitLoc.getWorld().getName().equals(world)) {\n                return;\n            }\n\n            // ???\n            if (Math.abs(playerChunk.getX() - bukkitLoc.getChunk().getX()) \u003e 5) {\n                return;\n            }\n\n            player.spawnParticle(particle, bukkitLoc, 1);\n        });\n    }\n}\n```\n\n**If you are interested in exploring functional programming and its applications within this project visit the repository at [vavr-in-action](https://github.com/noyzys/bukkit-vavr-in-action), [fp-practice](https://github.com/noyzys/fp-practice).**\n\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fnoyzys%2Fbukkit-region","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fnoyzys%2Fbukkit-region","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fnoyzys%2Fbukkit-region/lists"}