User prompt
make the room price 10
User prompt
Make the total number of rooms 60
User prompt
vertically center the two texts in the add room button inside the button
User prompt
Open the spaces between the rooms vertically
User prompt
Do not admit customers to rooms that are broken down
User prompt
create new image for broken room
User prompt
Each room will appear damaged after a random number of guests. A fee of between 20 and 300 will be charged to repair the damage.
User prompt
Customers who use 1 to 10 random items from the following shop can leave a price.
User prompt
The hotel name text should appear 30 pixels above the hotel.
User prompt
When the game starts, the hotel name is secret and added to the scoreboard with this name. ↪💡 Consider importing and using the following plugins: @upit/storage.v1
User prompt
add high score button on top right and make a popup ↪💡 Consider importing and using the following plugins: @upit/storage.v1
User prompt
keep the highest currency reached as score ↪💡 Consider importing and using the following plugins: @upit/storage.v1
User prompt
update room rates to $200
User prompt
move add room button down 30px
User prompt
move add room button down 30px
User prompt
vertically center text in add room button
User prompt
Add $200 text 30 pixels below the add room button
User prompt
move add room button 30px down
User prompt
move add room button 30px down
User prompt
hide rating section
User prompt
separate the images of the right and left navigation buttons.
User prompt
Each customer should pay a fee between $10 and $100 proportional to the hotel points they give. This fee should be added to the hotel budget.
User prompt
the money coming from the customer to the hotel budget. ↪💡 Consider importing and using the following plugins: @upit/storage.v1
User prompt
Customers pay a fee between $10 and $100 depending on the points they give. This fee is added to the hotel account. ↪💡 Consider importing and using the following plugins: @upit/storage.v1
User prompt
Don't let the room become full before the customer even gets to the room.
/**** * Plugins ****/ var tween = LK.import("@upit/tween.v1"); var storage = LK.import("@upit/storage.v1", { hotel0Rating: 0, hotel1Rating: 0, hotel2Rating: 0, hotel3Rating: 0, hotel4Rating: 0, hotel0RatingCount: 0, hotel1RatingCount: 0, hotel2RatingCount: 0, hotel3RatingCount: 0, hotel4RatingCount: 0 }); /**** * Classes ****/ var AddRoomButton = Container.expand(function () { var self = Container.call(this); var buttonBg = self.attachAsset('add_room_button', { anchorX: 0.5, anchorY: 0.5 }); self.buttonText = self.addChild(new Text2('Add Room', { size: 50, fill: 0xFFFFFF })); self.buttonText.anchor.set(0.5, 0.5); self.buttonText.x = 0; self.buttonText.y = 0; self.down = function (x, y, obj) { if (totalRooms < 50 && hotelCounts[currentHotelIndex] < 18 && budget >= 200) { if (hotels[currentHotelIndex].addRoom()) { totalRooms++; hotelCounts[currentHotelIndex]++; budget -= 200; // Deduct $200 for each room updateUI(); } } }; self.updateButton = function () { if (totalRooms >= 50 || hotelCounts[currentHotelIndex] >= 18 || budget < 200) { buttonBg.tint = 0x666666; if (hotelCounts[currentHotelIndex] >= 18) { self.buttonText.setText('Hotel Full'); } else if (budget < 200) { self.buttonText.setText('Need $200'); } else { self.buttonText.setText('Limit Reached'); } } else { buttonBg.tint = 0xffffff; self.buttonText.setText('Add Room'); } }; return self; }); var Customer = Container.expand(function () { var self = Container.call(this); var customerGraphics = self.attachAsset('customer', { anchorX: 0.5, anchorY: 1.0 }); self.isAtHotel = true; self.isMoving = false; self.moveToGroceryStore = function () { if (self.isMoving || !self.isAtHotel) return; self.isMoving = true; tween(self, { y: 2400 }, { duration: 2000, easing: tween.easeInOut, onFinish: function onFinish() { self.isAtHotel = false; self.isMoving = false; // Free the room when customer leaves if (self.occupiedRoomIndex !== undefined) { hotels[currentHotelIndex].setRoomOccupation(self.occupiedRoomIndex, false); self.occupiedRoomIndex = undefined; } // Stay at grocery store for a moment, then return LK.setTimeout(function () { self.returnToHotel(); }, 1500); } }); }; self.returnToHotel = function () { if (self.isMoving || self.isAtHotel) return; self.isMoving = true; // Calculate target position based on room location (customer already has a room) var targetX = 1024; // Default hotel center var targetY = 1366; // Default hotel center if (self.occupiedRoomIndex !== undefined) { // Re-occupy the same room when returning hotels[currentHotelIndex].setRoomOccupation(self.occupiedRoomIndex, true); // Calculate room position using same logic as in Hotel.updateDisplay var positions = []; for (var row = 0; row < 6; row++) { for (var col = 0; col < 3; col++) { positions.push({ x: (col - 1) * 240, y: (row - 2.5) * 130 }); } } if (self.occupiedRoomIndex < positions.length) { targetX = 1024 + positions[self.occupiedRoomIndex].x; // Add hotel offset targetY = 1366 + positions[self.occupiedRoomIndex].y; // Add hotel offset } } tween(self, { x: targetX, y: targetY }, { duration: 2000, easing: tween.easeInOut, onFinish: function onFinish() { self.isAtHotel = true; self.isMoving = false; // Complete scoring task and give rating if (self.scoringTask && !self.hasCompletedTask) { self.hasCompletedTask = true; var taskSuccess = checkTaskCompletion(self.scoringTask); var rating = taskSuccess ? Math.floor(Math.random() * 2) + 4 : Math.floor(Math.random() * 3) + 1; // 4-5 for success, 1-3 for failure // Calculate payment proportional to rating ($10-$100 based on 1-5 star rating) var payment = Math.floor(rating / 5 * 90) + 10; // Maps 1-5 stars to $10-$100 budget += payment; // Auto-rate the hotel based on task completion var ratingKey = 'hotel' + currentHotelIndex + 'Rating'; var countKey = 'hotel' + currentHotelIndex + 'RatingCount'; var currentRating = storage[ratingKey] || 0; var currentCount = storage[countKey] || 0; var totalScore = currentRating * currentCount + rating; var newCount = currentCount + 1; var newRating = totalScore / newCount; storage[ratingKey] = newRating; storage[countKey] = newCount; updateUI(); } } }); }; return self; }); var GroceryStore = Container.expand(function () { var self = Container.call(this); var storeBg = self.attachAsset('grocery_store', { anchorX: 0.5, anchorY: 0.5 }); self.storeText = self.addChild(new Text2('Grocery Store', { size: 40, fill: 0xFFFFFF })); self.storeText.anchor.set(0.5, 0.5); return self; }); var Hotel = Container.expand(function () { var self = Container.call(this); // Hotel background var hotelBg = self.attachAsset('hotel_bg', { anchorX: 0.5, anchorY: 0.5 }); // Properties self.hotelId = 1; self.roomCount = 0; self.rooms = []; self.occupiedRooms = []; // Track which rooms are occupied self.setHotel = function (id) { self.hotelId = id; self.updateDisplay(); }; self.addRoom = function () { if (self.roomCount < 18) { // Max 18 rooms per hotel (3x6 grid) var room = self.addChild(LK.getAsset('room_empty', { anchorX: 0.5, anchorY: 0.5 })); // Position rooms in 3x6 grid layout (3 columns, 6 rows) var positions = []; for (var row = 0; row < 6; row++) { for (var col = 0; col < 3; col++) { positions.push({ x: (col - 1) * 240, // Center the grid: -240, 0, 240 y: (row - 2.5) * 130 // Center vertically around hotel: -325, -195, -65, 65, 195, 325 }); } } var targetX = positions[self.roomCount].x; var targetY = positions[self.roomCount].y; // Check for overlapping with existing rooms var isOverlapping = false; for (var i = 0; i < self.rooms.length; i++) { var existingRoom = self.rooms[i]; var distanceX = Math.abs(existingRoom.x - targetX); var distanceY = Math.abs(existingRoom.y - targetY); // Check if rooms would overlap (room width is 150, height is 112.5, grid spacing is 240x130) if (distanceX < 240 && distanceY < 130) { isOverlapping = true; break; } } // If overlapping, try to find an alternative position if (isOverlapping) { var foundPosition = false; // Try different directional positions for (var tryPos = 0; tryPos < positions.length && !foundPosition; tryPos++) { if (tryPos === self.roomCount) continue; // Skip the current position targetX = positions[tryPos].x; targetY = positions[tryPos].y; isOverlapping = false; // Check this position against all existing rooms for (var i = 0; i < self.rooms.length; i++) { var existingRoom = self.rooms[i]; var distanceX = Math.abs(existingRoom.x - targetX); var distanceY = Math.abs(existingRoom.y - targetY); if (distanceX < 240 && distanceY < 130) { isOverlapping = true; break; } } if (!isOverlapping) { foundPosition = true; } } // If no position found, don't add the room if (!foundPosition) { room.destroy(); return false; } } room.x = targetX; room.y = targetY; // Room starts as empty (using room_empty asset) self.rooms.push(room); self.occupiedRooms.push(false); // Room starts as empty self.roomCount++; return true; } return false; }; self.updateDisplay = function () { // Clear existing rooms for (var i = 0; i < self.rooms.length; i++) { self.rooms[i].destroy(); } self.rooms = []; // Add rooms based on current count using 3x6 grid layout var positions = []; for (var row = 0; row < 6; row++) { for (var col = 0; col < 3; col++) { positions.push({ x: (col - 1) * 240, // Center the grid: -240, 0, 240 y: (row - 2.5) * 130 // Center vertically around hotel: -325, -195, -65, 65, 195, 325 }); } } for (var i = 0; i < self.roomCount; i++) { // Use appropriate room asset based on occupation status var assetName = self.occupiedRooms[i] ? 'room_full' : 'room_empty'; var room = self.addChild(LK.getAsset(assetName, { anchorX: 0.5, anchorY: 0.5 })); room.x = positions[i].x; room.y = positions[i].y; // Add click interaction to toggle occupation room.roomIndex = i; room.down = function (x, y, obj) { self.toggleRoomOccupation(this.roomIndex); }; self.rooms.push(room); } }; self.toggleRoomOccupation = function (roomIndex) { if (roomIndex >= 0 && roomIndex < self.roomCount) { self.occupiedRooms[roomIndex] = !self.occupiedRooms[roomIndex]; // Update room visual by refreshing display self.updateDisplay(); } }; self.setRoomOccupation = function (roomIndex, isOccupied) { if (roomIndex >= 0 && roomIndex < self.roomCount) { self.occupiedRooms[roomIndex] = isOccupied; // Update room visual by refreshing display self.updateDisplay(); } }; return self; }); var NavigationButton = Container.expand(function () { var self = Container.call(this); self.isLeft = true; self.buttonBg = null; self.buttonText = null; self.setDirection = function (isLeft) { self.isLeft = isLeft; // Remove existing background if it exists if (self.buttonBg) { self.removeChild(self.buttonBg); } // Create new background with appropriate asset var assetName = isLeft ? 'nav_button_left' : 'nav_button_right'; self.buttonBg = self.attachAsset(assetName, { anchorX: 0.5, anchorY: 0.5 }); }; // Initialize with default direction self.setDirection(true); self.setText = function (text) { if (self.buttonText) { self.buttonText.destroy(); } self.buttonText = self.addChild(new Text2(text, { size: 40, fill: 0xFFFFFF })); self.buttonText.anchor.set(0.5, 0.5); }; self.down = function (x, y, obj) { if (self.isLeft) { currentHotelIndex = (currentHotelIndex - 1 + 5) % 5; } else { currentHotelIndex = (currentHotelIndex + 1) % 5; } updateHotelDisplay(); }; return self; }); var RatingButton = Container.expand(function () { var self = Container.call(this); self.stars = []; self.hotelIndex = 0; self.currentRating = 0; // Create 5 star buttons for (var i = 0; i < 5; i++) { var star = self.addChild(LK.getAsset('nav_button_left', { anchorX: 0.5, anchorY: 0.5 })); star.scaleX = 0.6; star.scaleY = 0.6; star.x = (i - 2) * 80; // Space stars horizontally star.tint = 0x666666; // Gray by default star.starIndex = i + 1; // Add star text var starText = star.addChild(new Text2('★', { size: 30, fill: 0xFFFFFF })); starText.anchor.set(0.5, 0.5); star.down = function (x, y, obj) { self.setRating(this.starIndex); }; self.stars.push(star); } self.setHotelIndex = function (index) { self.hotelIndex = index; self.updateDisplay(); }; self.setRating = function (rating) { self.currentRating = rating; // Update visual stars for (var i = 0; i < 5; i++) { if (i < rating) { self.stars[i].tint = 0xFFD700; // Gold for selected stars } else { self.stars[i].tint = 0x666666; // Gray for unselected } } // Save rating to storage var ratingKey = 'hotel' + self.hotelIndex + 'Rating'; var countKey = 'hotel' + self.hotelIndex + 'RatingCount'; var currentRating = storage[ratingKey] || 0; var currentCount = storage[countKey] || 0; // Calculate new average rating var totalScore = currentRating * currentCount + rating; var newCount = currentCount + 1; var newRating = totalScore / newCount; storage[ratingKey] = newRating; storage[countKey] = newCount; // Update UI updateUI(); }; self.updateDisplay = function () { var ratingKey = 'hotel' + self.hotelIndex + 'Rating'; var rating = storage[ratingKey] || 0; // Show current average rating for (var i = 0; i < 5; i++) { if (i < Math.round(rating)) { self.stars[i].tint = 0xFFD700; // Gold for rated stars } else { self.stars[i].tint = 0x666666; // Gray for unrated } } }; return self; }); /**** * Initialize Game ****/ var game = new LK.Game({ backgroundColor: 0x2c3e50 }); /**** * Game Code ****/ // Game state variables var hotels = []; var currentHotelIndex = 0; var totalRooms = 0; var hotelCounts = [0, 0, 0, 0, 0]; var budget = 1000; // UI elements var hotelNameText; var currentRoomsText; var totalRoomsText; var budgetText; var ratingText; var leftButton; var rightButton; var addRoomButton; var ratingButton; var currentHotel; // Initialize hotels for (var i = 0; i < 5; i++) { hotels.push(new Hotel()); } // Initialize hotel counts to match hotel room counts for (var i = 0; i < 5; i++) { hotelCounts[i] = hotels[i].roomCount; } // Position current hotel in center currentHotel = game.addChild(hotels[0]); currentHotel.x = 1024; currentHotel.y = 1366; // Create navigation buttons leftButton = game.addChild(new NavigationButton()); leftButton.setDirection(true); leftButton.setText('<'); leftButton.x = 400; leftButton.y = 1366; rightButton = game.addChild(new NavigationButton()); rightButton.setDirection(false); rightButton.setText('>'); rightButton.x = 1648; rightButton.y = 1366; // Create add room button addRoomButton = game.addChild(new AddRoomButton()); addRoomButton.x = 1024; addRoomButton.y = 2020; // Create rating button (hidden) ratingButton = new RatingButton(); ratingButton.x = 1024; ratingButton.y = 2100; ratingButton.setHotelIndex(0); // Create UI text elements hotelNameText = new Text2('Hotel 1', { size: 80, fill: 0xFFFFFF }); hotelNameText.anchor.set(0.5, 0); LK.gui.top.addChild(hotelNameText); hotelNameText.y = 150; currentRoomsText = new Text2('Rooms in this hotel: 0', { size: 50, fill: 0xFFFFFF }); currentRoomsText.anchor.set(0.5, 0); LK.gui.top.addChild(currentRoomsText); currentRoomsText.y = 250; totalRoomsText = new Text2('Total rooms: 0/50', { size: 50, fill: 0xFFFFFF }); totalRoomsText.anchor.set(0.5, 0); LK.gui.top.addChild(totalRoomsText); totalRoomsText.y = 320; budgetText = new Text2('Budget: $1000', { size: 50, fill: 0xFFFFFF }); budgetText.anchor.set(0, 0); LK.gui.topLeft.addChild(budgetText); budgetText.x = 120; budgetText.y = 50; ratingText = new Text2('Rating: 0.0/5 (0 reviews)', { size: 50, fill: 0xFFFFFF }); ratingText.anchor.set(0.5, 0); ratingText.y = 390; function updateHotelDisplay() { // Remove current hotel game.removeChild(currentHotel); // Add new hotel currentHotel = game.addChild(hotels[currentHotelIndex]); currentHotel.x = 1024; currentHotel.y = 1366; currentHotel.setHotel(currentHotelIndex + 1); updateUI(); } function updateUI() { hotelNameText.setText('Hotel ' + (currentHotelIndex + 1)); currentRoomsText.setText('Rooms in this hotel: ' + hotelCounts[currentHotelIndex]); totalRoomsText.setText('Total rooms: ' + totalRooms + '/50'); budgetText.setText('Budget: $' + budget); addRoomButton.updateButton(); // Update rating display (hidden) var ratingKey = 'hotel' + currentHotelIndex + 'Rating'; var countKey = 'hotel' + currentHotelIndex + 'RatingCount'; var rating = storage[ratingKey] || 0; var count = storage[countKey] || 0; } // Update hotel counts when rooms are added function updateHotelCounts() { totalRooms = 0; for (var i = 0; i < 5; i++) { hotelCounts[i] = hotels[i].roomCount; totalRooms += hotelCounts[i]; } } game.update = function () { updateHotelCounts(); // Spawn customers at consistent intervals if there are rooms in the current hotel customerSpawnTimer++; if (customerSpawnTimer >= 150 && hotelCounts[currentHotelIndex] > 0 && customers.length < 8) { // Every 2.5 seconds consistently, max 8 customers customerSpawnTimer = 0; spawnCustomer(); } // Clean up customers that have been around too long for (var i = customers.length - 1; i >= 0; i--) { // Remove customers after they've made several trips (optional cleanup) if (Math.random() < 0.001) { // Very small chance to remove each frame customers[i].destroy(); customers.splice(i, 1); } } }; // Create grocery store at bottom of screen var groceryStore = game.addChild(new GroceryStore()); groceryStore.x = 1024; groceryStore.y = 2500; // Customer management var customers = []; var customerSpawnTimer = 0; function spawnCustomer() { var customer = game.addChild(new Customer()); customer.x = 900 + Math.random() * 248; // Random position near hotel customer.y = -100; // Start off-screen at the top customers.push(customer); // Find an available room position for the customer var availableRooms = []; for (var roomIdx = 0; roomIdx < hotels[currentHotelIndex].roomCount; roomIdx++) { if (!hotels[currentHotelIndex].occupiedRooms[roomIdx]) { availableRooms.push(roomIdx); } } // If no rooms available, show angry bubble and make customer leave with low rating if (availableRooms.length === 0) { // Create angry word bubble var angryBubble = customer.addChild(new Text2('😠', { size: 60, fill: 0xFF0000 })); angryBubble.anchor.set(0.5, 1); angryBubble.y = -50; // Make customer leave immediately with angry animation tween(customer, { y: -200 }, { duration: 1000, easing: tween.easeInOut, onFinish: function onFinish() { // Give low rating before leaving var ratingKey = 'hotel' + currentHotelIndex + 'Rating'; var countKey = 'hotel' + currentHotelIndex + 'RatingCount'; var currentRating = storage[ratingKey] || 0; var currentCount = storage[countKey] || 0; var lowRating = Math.floor(Math.random() * 2) + 1; // 1-2 stars // Calculate payment proportional to low rating ($10-$100 based on 1-5 star rating) var payment = Math.floor(lowRating / 5 * 90) + 10; // Maps 1-2 stars to $10-$28 budget += payment; var totalScore = currentRating * currentCount + lowRating; var newCount = currentCount + 1; var newRating = totalScore / newCount; storage[ratingKey] = newRating; storage[countKey] = newCount; updateUI(); // Remove customer for (var i = customers.length - 1; i >= 0; i--) { if (customers[i] === customer) { customers.splice(i, 1); break; } } customer.destroy(); } }); return; } // Calculate target position based on room layout var targetX = 1024; // Default hotel center var targetY = 1366; // Default hotel center // Use the first available room's position var roomIndex = availableRooms[0]; // Reserve the room index but don't occupy it yet customer.occupiedRoomIndex = roomIndex; // Calculate room position using same logic as in Hotel.updateDisplay var positions = []; for (var row = 0; row < 6; row++) { for (var col = 0; col < 3; col++) { positions.push({ x: (col - 1) * 240, y: (row - 2.5) * 130 }); } } if (roomIndex < positions.length) { targetX = 1024 + positions[roomIndex].x; // Add hotel offset targetY = 1366 + positions[roomIndex].y; // Add hotel offset } // Move customer to the specific room location tween(customer, { x: targetX, y: targetY }, { duration: 1500, easing: tween.easeInOut, onFinish: function onFinish() { // Occupy the room when customer actually arrives hotels[currentHotelIndex].setRoomOccupation(customer.occupiedRoomIndex, true); // Give customer a scoring task when they arrive at hotel customer.scoringTask = generateScoringTask(); customer.hasCompletedTask = false; // Customer goes to grocery store after arriving at hotel and a random delay LK.setTimeout(function () { customer.moveToGroceryStore(); }, Math.random() * 3000 + 1000); } }); } function generateScoringTask() { var tasks = [{ type: 'room_count', target: Math.floor(Math.random() * 10) + 5, description: 'Wants at least X rooms' }, { type: 'rating', target: Math.random() * 3 + 2, description: 'Expects rating above X' }, { type: 'budget', target: Math.floor(Math.random() * 500) + 200, description: 'Hotel should have budget above $X' }]; var task = tasks[Math.floor(Math.random() * tasks.length)]; // Customize target based on task type if (task.type === 'room_count') { task.target = Math.min(task.target, 15); // Max reasonable room expectation task.description = 'Wants at least ' + task.target + ' rooms'; } else if (task.type === 'rating') { task.target = Math.min(task.target, 4.5); // Max reasonable rating expectation task.description = 'Expects rating above ' + task.target.toFixed(1); } else if (task.type === 'budget') { task.description = 'Hotel should have budget above $' + task.target; } return task; } function checkTaskCompletion(task) { if (task.type === 'room_count') { return hotelCounts[currentHotelIndex] >= task.target; } else if (task.type === 'rating') { var ratingKey = 'hotel' + currentHotelIndex + 'Rating'; var currentRating = storage[ratingKey] || 0; return currentRating >= task.target; } else if (task.type === 'budget') { return budget >= task.target; } return false; } // Create cost text below add room button var costText = new Text2('$200', { size: 60, fill: 0xFFFFFF }); costText.anchor.set(0.5, 0); game.addChild(costText); costText.x = 1024; costText.y = 2050; // 30 pixels below add room button at y: 2020 // Initialize UI updateUI();
===================================================================
--- original.js
+++ change.js
@@ -31,24 +31,24 @@
self.buttonText.anchor.set(0.5, 0.5);
self.buttonText.x = 0;
self.buttonText.y = 0;
self.down = function (x, y, obj) {
- if (totalRooms < 50 && hotelCounts[currentHotelIndex] < 18 && budget >= 10) {
+ if (totalRooms < 50 && hotelCounts[currentHotelIndex] < 18 && budget >= 200) {
if (hotels[currentHotelIndex].addRoom()) {
totalRooms++;
hotelCounts[currentHotelIndex]++;
- budget -= 10; // Deduct $10 for each room
+ budget -= 200; // Deduct $200 for each room
updateUI();
}
}
};
self.updateButton = function () {
- if (totalRooms >= 50 || hotelCounts[currentHotelIndex] >= 18 || budget < 10) {
+ if (totalRooms >= 50 || hotelCounts[currentHotelIndex] >= 18 || budget < 200) {
buttonBg.tint = 0x666666;
if (hotelCounts[currentHotelIndex] >= 18) {
self.buttonText.setText('Hotel Full');
- } else if (budget < 10) {
- self.buttonText.setText('Need $10');
+ } else if (budget < 200) {
+ self.buttonText.setText('Need $200');
} else {
self.buttonText.setText('Limit Reached');
}
} else {
stickman top view. In-Game asset
empty room top view. In-Game asset. 2d. High contrast. No shadows
full room top view. In-Game asset. 2d. High contrast. No shadows
left arrow. In-Game asset
destroyed and damaged red flag cross the stripe
Hotel wall view from the front with flowers and mosses. In-Game asset
16:9
Building silhouettes. In-Game asset
hotel bar top view. In-Game asset