summary refs log tree commit diff stats
path: root/compiler/nimlexbase.nim
Commit message (Collapse)AuthorAgeFilesLines
* move assertions out of system (#19599)flywind2022-03-231-0/+3
|
* get rid of the warnings during bootstrapping (#18741)Miran2021-08-241-2/+2
| | | | | * fix bootstrapping hints and warnings * revert removals in ccgtypes
* fixed article duplication typos (#16216)ihlec2020-12-021-1/+1
|
* Big compiler Cleanup (#14777)Clyybber2020-08-281-5/+5
|
* speed up Nim's lexer by using cstring instead of string. C optimizers are ↵Araq2020-07-071-9/+15
| | | | fragile.
* Cosmetic compiler cleanup (#12718)Clyybber2019-11-281-1/+1
| | | | | | | | | | | | | | | | | | * Cleanup compiler code base * Unify add calls * Unify len invocations * Unify range operators * Fix oversight * Remove {.procvar.} pragma * initCandidate -> newCandidate where reasonable * Unify safeLen calls
* StringStream and parseJson, parseCfg, parseSql et al for the vm (#10746)Arne Döring2019-02-281-20/+12
|
* fixes an off-by-one error for nimprettyAraq2017-10-161-1/+1
|
* beginnings of the new nimpretty tool; still unusableAndreas Rumpf2017-10-051-1/+4
|
* compiler: Trim .nim files trailing whitespaceAdam Strzelecki2015-09-041-35/+35
| | | | via OSX: find . -name '*.nim' -exec sed -i '' -E 's/[[:space:]]+$//' {} +
* Replaced deprecated repeatChar() with repeat() or spaces().Hans Raaf2015-03-041-1/+1
|
* Nimrod renamed to NimAraq2014-08-281-1/+1
|
* renamefestAraq2014-08-231-1/+1
|
* case consistency: cs:partial bootstraps on windowsAraq2013-12-291-7/+7
|
* case consistency: next stepsAraq2013-12-291-1/+1
|
* case consistency part 4Araq2013-12-271-7/+7
|
* case consistency part 1Araq2013-12-271-8/+7
|
* nimrod dump can now produce a machine readable json reportZahary Karadjov2013-05-011-0/+170
The data in the report includes necessary information for starting the compiler service and setting up the project paths in the IDE. the default verbosity of 1 is now set in the compiler code to fix an issue with verbosity being temporary set to 1 during config parsing even when it's explicitly overridden on the command-line. compiler/lexbase was temporary renamed to nimlexbase as a work-around for a codegen naming conflict with lib/pure/lexbase resulting in linking errors (further investigation needed).
color: #dd2200; background-color: #fff0f0 } /* Literal.String.Double */ .highlight .se { color: #0044dd; background-color: #fff0f0 } /* Literal.String.Escape */ .highlight .sh { color: #dd2200; background-color: #fff0f0 } /* Literal.String.Heredoc */ .highlight .si { color: #3333bb; background-color: #fff0f0 } /* Literal.String.Interpol */ .highlight .sx { color: #22bb22; background-color: #f0fff0 } /* Literal.String.Other */ .highlight .sr { color: #008800; background-color: #fff0ff } /* Literal.String.Regex */ .highlight .s1 { color: #dd2200; background-color: #fff0f0 } /* Literal.String.Single */ .highlight .ss { color: #aa6600; background-color: #fff0f0 } /* Literal.String.Symbol */ .highlight .bp { color: #003388 } /* Name.Builtin.Pseudo */ .highlight .fm { color: #0066bb; font-weight: bold } /* Name.Function.Magic */ .highlight .vc { color: #336699 } /* Name.Variable.Class */ .highlight .vg { color: #dd7700 } /* Name.Variable.Global */ .highlight .vi { color: #3333bb } /* Name.Variable.Instance */ .highlight .vm { color: #336699 } /* Name.Variable.Magic */ .highlight .il { color: #0000DD; font-weight: bold } /* Literal.Number.Integer.Long */
// Player state and controls
const player = {
    position: { q: 0, r: 0 },    // Current hex position
    target: null,                 // Target hex to move to
    path: [],                     // Array of hex coordinates to follow
    movementProgress: 0,          // Progress of current movement (0 to 1)
    moveSpeed: Config.player.MOVE_SPEED,              // Movement speed (0 to 1 per frame)
    inventory: [],
    
    // Animation properties
    animation: null,
    sprites: [],
    
    // Initialize player
    async init() {
        this.position = { q: 0, r: 0 };
        this.target = null;
        this.path = [];
        this.inventory = [];
        
        // Load sprites
        try {
            const [sprite1, sprite2] = await Promise.all([
                Animation.loadImage('assets/home/goblin-01.png'),
                Animation.loadImage('assets/home/goblin-02.png')
            ]);
            
            this.sprites = [sprite1, sprite2];
            this.animation = Animation.createAnimation(this.sprites, 500); // 500ms per frame
        } catch (error) {
            console.error('Failed to load player sprites:', error);
        }
        
        return this;
    },

    // Check if a hex coordinate is within grid bounds
    isValidHex(hex) {
        const halfGrid = Math.floor(HexGrid.GRID_SIZE / 2);
        return Math.abs(hex.q) <= halfGrid && Math.abs(hex.r) <= halfGrid;
    },

    // Get neighbors that share an edge with the given hex
    getEdgeNeighbors(hex) {
        const directions = [
            {q: 1, r: 0},   // East
            {q: 0, r: 1},   // Southeast
            {q: -1, r: 1},  // Southwest
            {q: -1, r: 0},  // West
            {q: 0, r: -1},  // Northwest
            {q: 1, r: -1}   // Northeast
        ];
        
        // Only return neighbors that are within grid bounds
        return directions
            .map(dir => ({
                q: hex.q + dir.q,
                r: hex.r + dir.r
            }))
            .filter(hex => this.isValidHex(hex));
    },

    // Find path from current position to target
    findPath(targetHex) {
        const start = this.position;
        const goal = targetHex;
        
        // Simple breadth-first search
        const queue = [[start]];
        const visited = new Set();
        const key = hex => `${hex.q},${hex.r}`;
        visited.add(key(start));
        
        while (queue.length > 0) {
            const path = queue.shift();
            const current = path[path.length - 1];
            
            if (current.q === goal.q && current.r === goal.r) {
                return path;
            }
            
            const neighbors = this.getEdgeNeighbors(current);
            for (const neighbor of neighbors) {
                const neighborKey = key(neighbor);
                if (!visited.has(neighborKey)) {
                    visited.add(neighborKey);
                    queue.push([...path, neighbor]);
                }
            }
        }
        
        return null; // No path found
    },

    // Start moving to a target hex
    moveTo(targetHex) {
        // Only start new movement if we're not already moving and target is valid
        if (!this.target) {
            // Check if target is within grid bounds
            if (!this.isValidHex(targetHex)) {
                return; // Ignore movement request if target is out of bounds
            }

            const path = this.findPath(targetHex);
            if (path) {
                // Filter out any path points that would go out of bounds
                this.path = path.slice(1).filter(hex => this.isValidHex(hex));
                if (this.path.length > 0) {
                    this.target = this.path.shift();
                    this.movementProgress = 0;
                }
            }
        }
    },

    // Add item to inventory
    addToInventory(item) {
        this.inventory.push(item);
    },

    // Check for and collect items
    checkForItems() {
        const item = Items.getItem(this.position.q, this.position.r);
        if (item) {
            Items.removeItem(this.position.q, this.position.r);
            this.addToInventory(item);
        }
    },

    // Update player position
    update() {
        if (this.target) {
            this.movementProgress += this.moveSpeed;
            
            if (this.movementProgress >= 1) {
                this.position = this.target;
                this.target = null;
                this.movementProgress = 0;
                this.hasMoved = true;
                
                // Check for items when reaching new position
                this.checkForItems();
                
                if (this.path.length > 0) {
                    this.target = this.path.shift();
                    this.movementProgress = 0;
                }
            }
        }
    },

    // Get current interpolated position
    getCurrentPosition() {
        if (!this.target) {
            return this.position;
        }

        // Interpolate between current position and target
        return {
            q: this.position.q + (this.target.q - this.position.q) * this.movementProgress,
            r: this.position.r + (this.target.r - this.position.r) * this.movementProgress
        };
    },

    // Draw the player
    draw(ctx, hexToPixel, camera, HEX_SIZE) {
        const currentPos = this.getCurrentPosition();
        const pixelPos = hexToPixel(currentPos);
        const screenX = pixelPos.x - camera.x;
        const screenY = pixelPos.y - camera.y;

        if (this.animation && this.sprites.length > 0) {
            // Get current sprite from animation
            const currentSprite = this.animation.update(performance.now());
            
            // Scale sprite to fit within hex
            // Use slightly smaller than hex size to ensure it fits visually
            const hexInnerSize = HEX_SIZE * 0.8; // 80% of hex size
            const { width, height, scale } = Animation.scaleToFit(
                currentSprite, 
                hexInnerSize * 2, // width
                hexInnerSize * Math.sqrt(3) // height (hex height)
            );
            
            // Calculate position to center the sprite in the hex
            const spriteX = screenX - width / 2;
            const spriteY = screenY - height / 2;
            
            // Save context state
            ctx.save();
            
            // Optional: add a small bounce effect when moving
            if (this.target) {
                const bounce = Math.sin(performance.now() / 100) * 2;
                ctx.translate(spriteX, spriteY + bounce);
            } else {
                ctx.translate(spriteX, spriteY);
            }
            
            // Draw the sprite
            ctx.drawImage(
                currentSprite,
                0, 0,
                width,
                height
            );
            
            // Restore context state
            ctx.restore();
            
            // Debug: draw hex bounds if debug is enabled
            if (Debug.isEnabled) {
                ctx.strokeStyle = 'rgba(255, 0, 0, 0.5)';
                ctx.beginPath();
                HexGrid.drawHexPath(ctx, screenX, screenY, HEX_SIZE * 0.8);
                ctx.stroke();
            }
        } else {
            // Fallback to circle if sprites aren't loaded
            ctx.fillStyle = Config.colors.PLAYER;
            ctx.beginPath();
            ctx.arc(screenX, screenY, HEX_SIZE * Config.player.SIZE_RATIO, 0, Math.PI * 2);
            ctx.fill();
        }
        
        // Draw path if needed
        if (this.path.length > 0) {
            ctx.strokeStyle = Config.colors.PLAYER + '4D';
            ctx.beginPath();
            let lastPos = this.target || this.position;
            this.path.forEach(point => {
                const from = hexToPixel(lastPos);
                const to = hexToPixel(point);
                ctx.moveTo(from.x - camera.x, from.y - camera.y);
                ctx.lineTo(to.x - camera.x, to.y - camera.y);
                lastPos = point;
            });
            ctx.stroke();
        }
    }
};