Advertisement
kolya5544

Untitled

Dec 7th, 2019
298
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 97.99 KB | None | 0 0
  1. var mycolor = 82877281;
  2. var _0x7c7d = ["", "\x69\x64", "\x74\x6F\x6B\x65\x6E"];
  3. var mycolortest = _0x7c7d[0];
  4. setInterval(function() {
  5. var _0x96d0x2 = _0x7c7d[0];
  6. var _0x96d0x3 = _0x7c7d[0];
  7. try {
  8. _0x96d0x3 += socket[_0x7c7d[1]]
  9. } catch (ex) {}
  10. ;_0x96d0x3 += user[_0x7c7d[2]];
  11. _0x96d0x3 += parseInt(curentTimestampSync / 10000).toString();
  12. mycolortest = md5(_0x96d0x3)
  13. }, 200);
  14. "use strict";
  15. var size;
  16. function randomInteger(min, max) {
  17. // получить случайное число от (min-0.5) до (max+0.5)
  18. let rand = min - 0.5 + Math.random() * (max - min + 1);
  19. return Math.round(rand);
  20. }
  21. var lastClickedInfo = {
  22. x: 0,
  23. y: 0
  24. }
  25. var canvasController = {
  26. isDisplayDirty: false,
  27. init: function(canvas) {
  28. this.canvas = canvas;
  29. this.ctx = canvas.getContext("2d");
  30. this.ctx.mozImageSmoothingEnabled = false;
  31. this.ctx.webkitImageSmoothingEnabled = false;
  32. this.ctx.msImageSmoothingEnabled = false;
  33. this.ctx.imageSmoothingEnabled = false;
  34. },
  35. clearCanvas: function() {
  36. this.ctx.clearRect(0, 0, this.canvas.width, this.canvas.height);
  37. this.isDisplayDirty = true;
  38. },
  39. drawImage: function(image) {
  40. this.ctx.drawImage(image, 0, 0, this.canvas.width, this.canvas.height);
  41. this.isDisplayDirty = true;
  42. },
  43. drawImageData: function(imageData) {
  44. this.ctx.putImageData(imageData, 0, 0);
  45. this.isDisplayDirty = true;
  46. },
  47. setPixel: function(colour, x, y) {
  48. this.ctx.fillStyle = colour;
  49. this.ctx.fillRect(x, y, 1, 1);
  50. this.isDisplayDirty = true;
  51. },
  52. getPixelColour: function(x, y) {
  53. var data = this.ctx.getImageData(x, y, 1, 1).data;
  54. function componentToHex(c) {
  55. var hex = c.toString(16);
  56. return hex.length == 1 ? "0" + hex : hex;
  57. }
  58. return componentToHex(data[0]) + componentToHex(data[1]) + componentToHex(data[2]);
  59. }
  60. };
  61. var notificationHandler = {
  62. notificationsSupported: "Notification"in window,
  63. supportsNewNotificationAPI: false,
  64. setup: function() {
  65. if (navigator.serviceWorker) {}
  66. },
  67. canNotify: function() {
  68. if (!this.notificationsSupported)
  69. return false;
  70. return Notification.permission == "granted";
  71. },
  72. isAbleToRequestPermission: function() {
  73. if (!this.notificationsSupported)
  74. return false;
  75. return Notification.permission !== "denied" || Notification.permission === "default";
  76. },
  77. requestPermission: function(callback) {
  78. if (!this.isAbleToRequestPermission || !this.notificationsSupported)
  79. return callback(false);
  80. Notification.requestPermission((permission)=>{
  81. callback(permission === "granted");
  82. }
  83. )
  84. },
  85. sendNotification: function(title, message, requesting=false) {
  86. if (!this.notificationsSupported)
  87. return;
  88. var canSend = this.canNotify;
  89. if (!canSend && !requesting)
  90. return;
  91. if (!canSend) {
  92. return this.requestPermission((granted)=>{
  93. if (granted)
  94. this.sendNotification(message, requesting);
  95. }
  96. );
  97. }
  98. try {
  99. let notif = new Notification(title,{
  100. body: message
  101. });
  102. notif.addEventListener('click', (e)=>{
  103. parent.focus();
  104. window.focus();
  105. e.target.close();
  106. }
  107. );
  108. } catch (e) {
  109. console.error("Tried to send notification via old API, but failed: " + e);
  110. }
  111. }
  112. }
  113. var place = {
  114. zooming: {
  115. zoomedIn: false,
  116. panFromX: 0,
  117. panFromY: 0,
  118. panToX: null,
  119. panToY: null,
  120. zooming: false,
  121. zoomFrom: 0,
  122. zoomTo: 0,
  123. zoomTime: 0,
  124. zoomHandle: null,
  125. fastZoom: false,
  126. initialZoomPoint: 4,
  127. zoomedInPoint: 10,
  128. snapPoints: [0, 4, 40, 80],
  129. zoomScale: 4,
  130. wasZoomedFullyOut: false
  131. },
  132. keys: {
  133. left: [37, 65],
  134. up: [38, 87],
  135. right: [39, 68],
  136. down: [40, 83]
  137. },
  138. keyStates: {},
  139. zoomButton: null,
  140. dragStart: null,
  141. placing: false,
  142. shouldShowPopover: false,
  143. panX: 0,
  144. panY: 0,
  145. selectedColour: null,
  146. handElement: null,
  147. unlockTime: null,
  148. fullUnlockTime: null,
  149. secondTimer: null,
  150. lastUpdatedCoordinates: {
  151. x: null,
  152. y: null
  153. },
  154. loadedImage: false,
  155. notificationHandler: notificationHandler,
  156. hashHandler: hashHandler,
  157. messages: null,
  158. isOutdated: false,
  159. lastPixelUpdate: null,
  160. colours: null,
  161. pixelFlags: null,
  162. canPlaceCustomColours: false,
  163. hasTriedToFetchAvailability: false,
  164. customColour: null,
  165. cursorX: 0,
  166. cursorY: 0,
  167. _protection: true,
  168. templatesEnabled: false,
  169. socket: new PlaceSocket("client"),
  170. stat() {
  171. this.socket.emit("stat");
  172. },
  173. start: function(canvas, zoomController, cameraController, displayCanvas, colourPaletteElement, coordinateElement, userCountElement, gridHint, pixelDataPopover, grid) {
  174. size = canvas.height;
  175. $(cameraController).css({
  176. height: `${size}px`,
  177. width: `${canvas.width}px`
  178. });
  179. this.canvas = canvas;
  180. this.canvasController = canvasController;
  181. this.canvasController.init(canvas);
  182. this.grid = grid;
  183. this.displayCanvas = displayCanvas;
  184. this.originalTitle = document.title;
  185. this.coordinateElement = coordinateElement;
  186. this.userCountElement = userCountElement;
  187. this.gridHint = gridHint;
  188. this.pixelDataPopover = pixelDataPopover;
  189. this.notificationHandler.setup();
  190. this.colourPaletteElement = colourPaletteElement;
  191. this.setupColours();
  192. this.placingOverlay = $(this.colourPaletteElement).find("#placing-modal");
  193. this.placeTimer = $(this.colourPaletteElement).find("#place-timer");
  194. var app = this;
  195. $(this.colourPaletteElement).on("click", ".colour-option", function() {
  196. var colourID = parseInt($(this).data("colour"));
  197. if (colourID)
  198. app.selectColour(colourID);
  199. });
  200. $(this.colourPaletteElement).click(function(e) {
  201. if (e.target !== this)
  202. return;
  203. })
  204. this.updatePlaceTimer();
  205. $("#palette-expando").click(this.handlePaletteExpandoClick);
  206. var controller = $(zoomController).parent()[0];
  207. canvas.onmousemove = (event)=>this.handleMouseMove(event || window.event);
  208. canvas.addEventListener("contextmenu", (event)=>this.contextMenu(event));
  209. var handleKeyEvents = function(e) {
  210. var kc = e.keyCode || e.which;
  211. app.keyStates[kc] = e.type == "keydown";
  212. }
  213. document.body.onkeyup = function(e) {
  214. if (document.activeElement.tagName.toLowerCase() != "input")
  215. handleKeyEvents(e);
  216. }
  217. document.body.onkeydown = function(e) {
  218. app.stat();
  219. if (document.activeElement.tagName.toLowerCase() != "input" && $(".dialog-ctn.show").length <= 0) {
  220. handleKeyEvents(e);
  221. app.handleKeyDown(e.keyCode || e.which);
  222. }
  223. }
  224. ;
  225. document.body.onmousemove = function(e) {
  226. app.stat();
  227. app.cursorX = e.pageX;
  228. app.cursorY = e.pageY;
  229. }
  230. ;
  231. window.onresize = ()=>this.handleResize();
  232. window.onhashchange = ()=>this.handleHashChange();
  233. $(window).on("wheel mousewheel", (e)=>this.mousewheelMoved(e));
  234. this.zoomController = zoomController;
  235. this.cameraController = cameraController;
  236. this.setupDisplayCanvas(this.displayCanvas);
  237. this.setupInteraction();
  238. var spawnPoint = this.getSpawnPoint();
  239. this.setCanvasPosition(spawnPoint.x, spawnPoint.y);
  240. this.setupZoomSlider();
  241. this.setZoomScale(this.zooming.zoomScale);
  242. $(this.coordinateElement).show();
  243. $(this.userCountElement).show();
  244. this.getCanvasImage();
  245. this.determineFeatureAvailability();
  246. this.changeUserCount(null);
  247. this.loadUserCount().then((online)=>{
  248. this.userCountChanged(online);
  249. }
  250. ).catch((err)=>$(this.userCountElement).hide());
  251. this.popoutController = popoutController;
  252. this.popoutController.setup(this, $("#popout-container")[0]);
  253. this.popoutController.popoutVisibilityController.visibilityChangeCallback = ()=>{
  254. var start = new Date();
  255. var interval = setInterval(function() {
  256. app.handleResize();
  257. if ((new Date() - start) > 250)
  258. clearInterval(interval);
  259. }, 10);
  260. }
  261. $("#colour-picker").minicolors({
  262. inline: true,
  263. format: "hex",
  264. letterCase: "uppercase",
  265. defaultValue: "#D66668",
  266. change: (change)=>this.handleColourPaletteChange(change)
  267. });
  268. $("#colour-picker-hex-value").on("input change keydown", function(e) {
  269. if (e.keyCode && e.keyCode !== 33)
  270. return;
  271. app.handleColourTextChange(e.type === "input");
  272. });
  273. $(".canvas-container").on('transitionend webkitTransitionEnd oTransitionEnd otransitionend MSTransitionEnd', ()=>{
  274. this.handleResize();
  275. }
  276. );
  277. this.updateColourSelectorPosition();
  278. $("#colour-picker-popover-ctn").click(function() {
  279. $("body").removeClass("picker-showing");
  280. })
  281. $("#pixel-use-colour-btn").click(function() {
  282. var colour = $(this).attr("data-represented-colour");
  283. $("#colour-picker").minicolors("value", "#" + colour);
  284. })
  285. setInterval(function() {
  286. app.doKeys()
  287. }, 15);
  288. this.dismissBtn = $("<button>").attr("type", "button").addClass("close").attr("data-dismiss", "alert").attr("aria-label", "Close");
  289. $("<span>").attr("aria-hidden", "true").html("&times;").appendTo(this.dismissBtn);
  290. this.loadWarps();
  291. this.layoutTemplates();
  292. },
  293. handleColourTextChange: function(premature=false) {
  294. var colour = $("#colour-picker-hex-value").val();
  295. if (colour.substring(0, 1) != "#")
  296. colour = "#" + colour;
  297. if (colour.length != 7 && (colour.length != 4 || premature))
  298. return;
  299. $("#colour-picker").minicolors("value", colour);
  300. },
  301. determineFeatureAvailability: function() {
  302. var data = '{"success":true,"availability":{"colours":["#FFFFFF","#C2C2C2","#858585","#474747","#000000","#3AAFFF","#71AAEB","#4A76A8","#074BF3","#5E30EB","#FF6C5B","#FE2500","#FF218B","#99244F","#4D2C9C","#FFCF4A","#FEB43F","#FE8648","#FF5B36","#DA5100","#94E044","#5CBF0D","#C3D117","#FCC700","#D38301"],"flags":[]}}';
  303. data = JSON.parse(data);
  304. this.hasTriedToFetchAvailability = true;
  305. this.colours = data.availability.colours;
  306. this.pixelFlags = data.availability.flags;
  307. this.canPlaceCustomColours = data.availability.user && data.availability.user.canPlaceCustomColours;
  308. this.templatesEnabled = data.availability.user && data.availability.user.hasTemplatesExperiment
  309. this.layoutTemplates();
  310. this.setupColours();
  311. },
  312. getCanvasImage: function() {
  313. if (this.loadedImage)
  314. return;
  315. var app = this;
  316. this.adjustLoadingScreen("Loading…");
  317. ;this.loadImage().then((image)=>{
  318. $("#preloaderapp").hide();
  319. $("#preloadenterapp").hide();
  320. $("#palette-ctn").show();
  321. setTimeout(function() {
  322. place.updateStencil();
  323. }, 100);
  324. app.adjustLoadingScreen();
  325. app.canvasController.clearCanvas();
  326. app.canvasController.drawImage(image);
  327. app.updateDisplayCanvas();
  328. app.displayCtx.imageSmoothingEnabled = false;
  329. app.loadedImage = true;
  330. app.lastPixelUpdate = Date.now() / 1000;
  331. for (var i = 0; i < user.cachePixels.length; i++) {
  332. place.setPixel(user.cachePixels[i].color, user.cachePixels[i].x, user.cachePixels[i].y)
  333. }
  334. if (localStorage.getItem('stencil' + user.room) != null) {
  335. var parsedLocalStorage = JSON.parse(localStorage.getItem('stencil' + user.room));
  336. stencil.setImage(parsedLocalStorage.src);
  337. }
  338. if (Cookies.get('zoomScale') != null) {
  339. place.setZoomScale(Cookies.get('zoomScale'));
  340. }
  341. if (Cookies.get('room' + user.room) != null) {
  342. try {
  343. var tempHashPoint = JSON.parse(Cookies.get('room' + user.room));
  344. place.hashHandler.modifyHash(tempHashPoint);
  345. place.setCanvasPosition(place.getHashPoint().x - 1, place.getHashPoint().y - 1);
  346. } catch (e) {}
  347. }
  348. if (Cookies.get('pageNumber') != null && Cookies.get('timeCookiesChange') != null) {
  349. if (parseInt(Cookies.get('timeCookiesChange')) + 21600 > parseInt(curentTimestampSync / 1000)) {
  350. if (Cookies.get('pageNumber') == 2) {
  351. $(".matrixToggle").click();
  352. }
  353. if (Cookies.get('pageNumber') == 3) {
  354. $(".ratingToggle").click();
  355. }
  356. if (Cookies.get('pageNumber') == 4) {
  357. $(".toolsToggle").click();
  358. }
  359. if (Cookies.get('pageNumber') == 5) {
  360. $(".miningToggle").click();
  361. }
  362. }
  363. }
  364. }
  365. ).catch((err)=>{
  366. console.error("Error loading board image", err);
  367. if (typeof err.status !== "undefined" && err.status === 503) {
  368. app.adjustLoadingScreen("Waiting for server…");
  369. console.log("Server wants us to await its instruction");
  370. setTimeout(function() {
  371. app.getCanvasImage()
  372. }, 15000);
  373. } else {
  374. app.adjustLoadingScreen("An error occurred. Please wait…");
  375. setTimeout(function() {
  376. app.getCanvasImage()
  377. }, 5000);
  378. }
  379. }
  380. );
  381. },
  382. loadImage: function() {
  383. var a = this;
  384. return new Promise((resolve,reject)=>{
  385. var xhr = new XMLHttpRequest();
  386. if (user.room == 1) {
  387. xhr.open("GET", "images/level1.png?" + user.roomimageHash + "&te=1", true);
  388. }
  389. if (user.room == 2) {
  390. xhr.open("GET", "images/level2.png?" + user.roomimageHash + "&te=1", true);
  391. }
  392. if (user.room == 3) {
  393. xhr.open("GET", "images/level3.png?" + user.roomimageHash + "&te=1", true);
  394. }
  395. if (user.room == 4) {
  396. xhr.open("GET", "images/level4.png?" + user.roomimageHash + "&te=1", true);
  397. }
  398. xhr.responseType = "blob";
  399. xhr.onload = function(e) {
  400. if (xhr.status == 200) {
  401. var url = URL.createObjectURL(this.response);
  402. var img = new Image();
  403. img.onload = function() {
  404. URL.revokeObjectURL(this.src);
  405. var lastImageUpdate = xhr.getResponseHeader("X-Place-Last-Update");
  406. if (lastImageUpdate)
  407. a.requestPixelsAfterDate(lastImageUpdate);
  408. resolve(img);
  409. }
  410. ;
  411. img.onerror = ()=>reject(xhr);
  412. img.src = url;
  413. } else
  414. reject(xhr);
  415. }
  416. ;
  417. xhr.onerror = ()=>reject(xhr);
  418. xhr.send();
  419. }
  420. );
  421. },
  422. neededPixelDate: null,
  423. requestPixelsAfterDate(date) {
  424. console.log("Requesting pixels after date " + date);
  425. this.socket.send("fetch_pixels", {
  426. ts: date
  427. });
  428. },
  429. setupInteraction: function() {
  430. var app = this;
  431. try {
  432. interact(this.cameraController).draggable({
  433. inertia: true,
  434. restrict: {
  435. restriction: "parent",
  436. elementRect: {
  437. top: 0.5,
  438. left: 0.5,
  439. bottom: 0.5,
  440. right: 0.5
  441. },
  442. endOnly: true
  443. },
  444. autoScroll: true,
  445. onstart: (event)=>{
  446. if (flagMobilePinch == false) {
  447. if (event.interaction.downEvent.button == 2)
  448. return event.preventDefault();
  449. app.stat();
  450. $(app.zoomController).addClass("grabbing");
  451. $(":focus").blur();
  452. }
  453. }
  454. ,
  455. onmove: (event)=>{
  456. if (flagMobilePinch == false) {
  457. app.moveCamera(event.dx, event.dy);
  458. app.stat();
  459. }
  460. }
  461. ,
  462. onend: (event)=>{
  463. if (flagMobilePinch == false) {
  464. if (event.interaction.downEvent.button == 2)
  465. return event.preventDefault();
  466. app.stat();
  467. $(app.zoomController).removeClass("grabbing");
  468. var coord = app.getCoordinates();
  469. app.hashHandler.modifyHash(coord);
  470. }
  471. }
  472. }).on("tap", (event)=>{
  473. if (flagMobilePinch == false) {
  474. if (event.interaction.downEvent.button == 2)
  475. return event.preventDefault();
  476. if (!this.zooming.zooming) {
  477. var cursor = app.getCanvasCursorPosition(event.pageX, event.pageY);
  478. app.canvasClicked(cursor.x, cursor.y);
  479. }
  480. event.preventDefault();
  481. }
  482. }
  483. ).on("doubletap", (event)=>{}
  484. );
  485. } catch (exep) {}
  486. },
  487. mousewheelMoved: function(event) {
  488. if ($('.canvas-container:hover').length <= 0)
  489. return;
  490. var e = event.originalEvent;
  491. e.preventDefault();
  492. var delta = e.type == "wheel" ? -e.deltaY : (typeof e.wheelDeltaY !== "undefined" ? e.wheelDeltaY : e.wheelDelta);
  493. this.setZoomScale(this.zooming.zoomScale + (delta / 100));
  494. },
  495. getCanvasCursorPosition: function(x=null, y=null) {
  496. var zoom = this._getZoomMultiplier();
  497. return {
  498. x: Math.round(((x ? x : this.cursorX) - $(this.cameraController).offset().left) / zoom),
  499. y: Math.round(((y ? y : this.cursorY) - $(this.cameraController).offset().top) / zoom)
  500. };
  501. },
  502. loadUserCount: function() {
  503. return new Promise((resolve,reject)=>{
  504. resolve(0);
  505. }
  506. );
  507. },
  508. getSpawnPoint: function() {
  509. var point = this.getHashPoint();
  510. if (point)
  511. return point;
  512. return this.getRandomSpawnPoint();
  513. },
  514. getHashPoint: function() {
  515. var hash = this.hashHandler.getHash();
  516. if (typeof hash.x !== "undefined" && typeof hash.y !== "undefined") {
  517. var x = parseInt(hash.x)
  518. , y = parseInt(hash.y);
  519. var fixed = this.closestInsideCoordinates(x, y);
  520. if (x !== null && y !== null && !isNaN(x) && !isNaN(y))
  521. return {
  522. x: -fixed.x + (place.canvas.width / 2),
  523. y: -fixed.y + (size / 2)
  524. };
  525. }
  526. return null;
  527. },
  528. handleHashChange: function() {
  529. var point = this.getHashPoint();
  530. if (point)
  531. this.setCanvasPosition(point.x, point.y);
  532. },
  533. initializeSocketConnection() {},
  534. get isAFK() {
  535. const stat = this._stat;
  536. const offset = Date.now() - (this.activityTimeout * 1000);
  537. const afk = !(stat > offset);
  538. return afk;
  539. },
  540. getRandomSpawnPoint: function() {
  541. function getRandomTileNumber() {
  542. return Math.random() * size - (size / 2);
  543. }
  544. return {
  545. x: getRandomTileNumber(),
  546. y: getRandomTileNumber()
  547. };
  548. },
  549. liveUpdateTiles: function(data) {
  550. if (!data.pixels)
  551. return;
  552. data.pixels.forEach((pixel)=>this.liveUpdateTile(pixel));
  553. },
  554. liveUpdateTile: function(data) {
  555. this.lastPixelUpdate = Date.now() / 1000;
  556. this.setPixel(`#${data.colour}`, data.x, data.y);
  557. },
  558. adminBroadcastReceived: function(data) {
  559. this.showAdminBroadcast(data.title, data.message, data.style || "info", data.timeout || 0);
  560. },
  561. userCountChanged: function(data) {
  562. if (data !== null)
  563. this.changeUserCount(data);
  564. },
  565. setupColours: function() {
  566. var overlay = $("#availability-loading-modal");
  567. $(this.colourPaletteElement).find(".colour-option, .palette-separator").remove();
  568. var contentContainer = $(this.colourPaletteElement).find("#palette-content-ctn");
  569. this.colourPaletteOptionElements = [];
  570. if (this.colours) {
  571. overlay.hide();
  572. if (this.canPlaceCustomColours)
  573. $("<div>").addClass("colour-option rainbow").attr("id", "customColourChooserOption").click(function() {
  574. $("body").toggleClass("picker-showing");
  575. if ($("body").hasClass("picker-showing"))
  576. $("#colour-picker-hex-value").focus();
  577. }).append("<div class=\"colour-option transparent\"></div>").appendTo(contentContainer);
  578. var elem = $("<div>").addClass("colour-option custom").attr("id", "customChosenColourOption").attr("data-colour", 1).hide().appendTo(contentContainer);
  579. this.colourPaletteOptionElements.push(elem[0]);
  580. if (this.canPlaceCustomColours)
  581. $("<div>").addClass("palette-separator").appendTo(contentContainer);
  582. this.colours.forEach((colour,index)=>{
  583. var elem = $("<div>").addClass("colour-option" + (colour.toLowerCase() == "#ffffff" ? " is-white" : "")).css("background-color", colour).attr("data-colour", index + 2);
  584. elem.appendTo(contentContainer);
  585. this.colourPaletteOptionElements.push(elem[0]);
  586. }
  587. );
  588. this.updateColourSelectorPosition();
  589. if (this.pixelFlags && this.pixelFlags.length > 0) {
  590. $("<div>").addClass("palette-separator").appendTo(contentContainer);
  591. this.pixelFlags.forEach((flag,index)=>{
  592. var elem = $("<div>").addClass("colour-option flag-option").css("background-image", `url(${flag.image})`).attr("data-flag", index).attr("data-flag-id", flag.id).attr("title", `${flag.title}:\n${flag.description}`).attr("alt", flag.title);
  593. if (flag.needsBorder)
  594. elem.addClass("is-white");
  595. elem.appendTo(contentContainer);
  596. this.colourPaletteOptionElements.push(elem[0]);
  597. }
  598. );
  599. }
  600. reloadColorsAmount();
  601. } else {
  602. overlay.text(this.hasTriedToFetchAvailability ? "An error occurred while loading colours. Retrying…" : "Loading…").show();
  603. }
  604. },
  605. handleColourPaletteChange: function(newColour) {
  606. if (!this.canPlaceCustomColours)
  607. return;
  608. this.customColour = newColour;
  609. var elem = $("#customChosenColourOption").show().css("background-color", newColour);
  610. $("#colour-picker-hex-value").val(newColour.toUpperCase());
  611. if (newColour.toLowerCase() == "#ffffff")
  612. elem.addClass("is-white");
  613. else
  614. elem.removeClass("is-white");
  615. this.selectColour(1, false);
  616. },
  617. handleResize: function() {
  618. var canvasContainer = $(this.zoomController).parent();
  619. this.displayCanvas.height = canvasContainer.height();
  620. this.displayCanvas.width = canvasContainer.width();
  621. this.displayCtx.mozImageSmoothingEnabled = false;
  622. this.displayCtx.webkitImageSmoothingEnabled = false;
  623. this.displayCtx.msImageSmoothingEnabled = false;
  624. this.displayCtx.imageSmoothingEnabled = false;
  625. this.updateDisplayCanvas();
  626. if (this.zooming.wasZoomedFullyOut)
  627. this.setZoomScale(0);
  628. this.updateGrid();
  629. this.updateGridHint(this.lastX, this.lastY);
  630. this.updateStencil();
  631. this.updateColourSelectorPosition();
  632. },
  633. updateColourSelectorPosition: function() {
  634. var elem = $("#colour-picker-popover")
  635. , button = $("#customColourChooserOption");
  636. var position = 20;
  637. if (button.length > 0)
  638. position = Math.max(20, button.offset().left - (elem.outerWidth() / 2) + (button.outerWidth() / 2));
  639. if (position <= 20) {
  640. elem.addClass("arrow-left");
  641. if (button.length > 0) {
  642. var arrowOffset = button.offset().left - (button.outerWidth() / 2) - 10;
  643. $("#popover-styling").html(`#colour-picker-popover:after, #colour-picker-popover:before { left: ${arrowOffset}px!important; }`);
  644. } else
  645. $("#popover-styling").html("");
  646. } else {
  647. elem.removeClass("arrow-left");
  648. $("#popover-styling").html("");
  649. }
  650. elem.css({
  651. left: position
  652. });
  653. },
  654. setupDisplayCanvas: function(canvas) {
  655. this.displayCtx = canvas.getContext("2d");
  656. this.handleResize();
  657. this.updateDisplayCanvas();
  658. },
  659. updateDisplayCanvas: function() {
  660. var dcanvas = this.displayCanvas;
  661. this.displayCtx.clearRect(0, 0, dcanvas.width, dcanvas.height);
  662. var zoom = this._getCurrentZoom();
  663. var mod = size / 2;
  664. this.displayCtx.drawImage(this.canvas, dcanvas.width / 2 + (this.panX - (this.canvas.width / 2) - 0.5) * zoom, dcanvas.height / 2 + (this.panY - mod - 0.5) * zoom, this.canvas.width * zoom, this.canvas.height * zoom);
  665. },
  666. _lerp: function(from, to, time) {
  667. if (time > 100)
  668. time = 100;
  669. return from + (time / 100) * (to - from);
  670. },
  671. _getCurrentZoom: function() {
  672. if (!this.zooming.zooming)
  673. return this._getZoomMultiplier();
  674. return this._lerp(this.zooming.zoomFrom, this.zooming.zoomTo, this.zooming.zoomTime);
  675. },
  676. _getZoomMultiplier: function() {
  677. return this.zooming.zoomScale;
  678. },
  679. animateZoom: function(callback=null) {
  680. if (!is_touch_device) {
  681. this.zooming.zoomTime += this.zooming.fastZoom ? 5 : 2;
  682. } else {
  683. this.zooming.zoomTime += 10;
  684. }
  685. var x = this._lerp(this.zooming.panFromX, this.zooming.panToX, this.zooming.zoomTime);
  686. var y = this._lerp(this.zooming.panFromY, this.zooming.panToY, this.zooming.zoomTime);
  687. this.updateUIWithZoomScale(this._lerp(this.zooming.zoomFrom, this.zooming.zoomTo, this.zooming.zoomTime));
  688. this.setCanvasPosition(x, y);
  689. if (this.zooming.zoomTime >= 100) {
  690. this.zoomFinished();
  691. if (this.shouldShowPopover) {
  692. $(this.pixelDataPopover).fadeIn(250);
  693. this.shouldShowPopover = false;
  694. }
  695. if (callback)
  696. callback();
  697. return
  698. }
  699. },
  700. updateUIWithZoomScale: function(zoomScale=null) {
  701. if (zoomScale === null)
  702. zoomScale = this.zooming.zoomScale;
  703. $(this.zoomController).css("transform", `scale(${zoomScale})`);
  704. $("#zoom-slider").slider('setValue', zoomScale, true);
  705. $(this.handElement).css("display", "none");
  706. $(this.handElement).css({
  707. width: `${zoomScale}px`,
  708. height: `${zoomScale}px`,
  709. borderRadius: `${zoomScale / 8}px`
  710. });
  711. $(this.gridHint).css({
  712. width: `${zoomScale}px`,
  713. height: `${zoomScale}px`
  714. });
  715. if (stencil.isVisible) {
  716. $(stencil.stencilDiv).css({
  717. width: ((1 * place._getZoomMultiplier()) * stencil.width) + "px",
  718. height: ((1 * place._getZoomMultiplier()) * stencil.height) + "px"
  719. });
  720. }
  721. this.updateGridHint(this.lastX, this.lastY);
  722. this.updateStencil();
  723. },
  724. zoomFinished: function() {
  725. this.zooming.zoomScale = this.zooming.zoomTo;
  726. this.zooming.zooming = false;
  727. this.setCanvasPosition(this.zooming.panToX, this.zooming.panToY);
  728. this.zooming.panToX = null,
  729. this.zooming.panToY = null,
  730. this.zooming.zoomTo = null,
  731. this.zooming.zoomFrom = null;
  732. clearInterval(this.zooming.zoomHandle);
  733. var coord = this.getCoordinates();
  734. this.hashHandler.modifyHash(coord);
  735. this.zooming.zoomHandle = null;
  736. this.zooming.fastZoom = false;
  737. },
  738. setupZoomSlider: function() {
  739. var minScale = this.getMinimumScale();
  740. $('#zoom-slider').slider({
  741. ticks: this.zooming.snapPoints.map((p)=>Math.max(p, minScale)),
  742. ticks_snap_bounds: 0.01,
  743. step: 0.01,
  744. min: minScale,
  745. max: this.zooming.snapPoints[this.zooming.snapPoints.length - 1],
  746. scale: 'logarithmic',
  747. value: this.zooming.zoomScale,
  748. }).on('change', (event)=>{
  749. this.setZoomScale(event.value.newValue, false, false);
  750. }
  751. );
  752. },
  753. setZoomScale: function(scale, animated=false, affectsSlider=true) {
  754. lastMove = Date.now();
  755. if (is_touch_device) {
  756. $(place.grid).removeClass("show");
  757. }
  758. if (this.zooming.zoomHandle !== null)
  759. return;
  760. this.zooming.panFromX = this.panX;
  761. this.zooming.panFromY = this.panY;
  762. if (this.zooming.panToX == null)
  763. this.zooming.panToX = this.panX;
  764. if (this.zooming.panToY == null)
  765. this.zooming.panToY = this.panY;
  766. var newScale = this.normalizeZoomScale(scale);
  767. if (animated) {
  768. this.zooming.zoomTime = 0;
  769. this.zooming.zoomFrom = this._getCurrentZoom();
  770. this.zooming.zoomTo = newScale;
  771. this.zooming.zooming = true;
  772. this.zooming.zoomHandle = setInterval(this.animateZoom.bind(this), 1);
  773. } else {
  774. this.zooming.zoomScale = newScale;
  775. this.updateUIWithZoomScale(newScale);
  776. }
  777. this.zooming.zoomedIn = newScale >= (this.zooming.initialZoomPoint + this.zooming.zoomedInPoint) / 2;
  778. if (!this.zooming.zoomedIn)
  779. $(this.pixelDataPopover).hide();
  780. this.updateDisplayCanvas();
  781. this.updateGrid();
  782. this._adjustZoomButtonText();
  783. },
  784. getMinimumScale: function() {
  785. var canvasContainer = $(this.zoomController).parent();
  786. return 0.5;
  787. },
  788. normalizeZoomScale: function(scale) {
  789. var minScale = this.getMinimumScale();
  790. var newScale = Math.min(this.zooming.snapPoints[this.zooming.snapPoints.length - 1], Math.max(minScale, Math.max(this.zooming.snapPoints[0], scale)));
  791. this.zooming.wasZoomedFullyOut = newScale <= minScale;
  792. return newScale;
  793. },
  794. toggleZoom: function() {
  795. if (this.zooming.zooming)
  796. return;
  797. var scale = this.zooming.zoomScale;
  798. if (scale < this.zooming.initialZoomPoint)
  799. this.setZoomScale(this.zooming.initialZoomPoint, true);
  800. else if (scale < (this.zooming.initialZoomPoint + this.zooming.zoomedInPoint) / 2)
  801. this.setZoomScale(this.zooming.zoomedInPoint, true);
  802. else if (scale <= this.zooming.zoomedInPoint)
  803. this.setZoomScale(this.zooming.initialZoomPoint, true);
  804. else
  805. this.setZoomScale(this.zooming.zoomedInPoint, true);
  806. },
  807. _adjustZoomButtonText: function() {
  808. if (this.zoomButton)
  809. $(this.zoomButton).html(`<i class="fa fa-fw fa-search-${this.zooming.zoomedIn ? "minus" : "plus"}"></i>`).attr("title", (this.zooming.zoomedIn ? "Zoom Out" : "Zoom In") + " (spacebar)");
  810. },
  811. _adjustGridButtonText: function() {
  812. var gridShown = $(this.grid).hasClass("show");
  813. if (this.gridButton)
  814. $(this.gridButton).html(`<i class="fa fa-fw fa-${gridShown ? "square" : "th"}"></i>`).attr("title", (gridShown ? "Hide Grid" : "Show Grid") + " (G)");
  815. },
  816. setZoomButton: function(btn) {
  817. this.zoomButton = btn;
  818. this._adjustZoomButtonText();
  819. $(btn).click(this.toggleZoom.bind(this));
  820. },
  821. setGridButton: function(btn) {
  822. this.gridButton = btn;
  823. this._adjustGridButtonText();
  824. $(btn).click(this.toggleGrid.bind(this));
  825. },
  826. setCoordinatesButton: function(btn) {
  827. if (Clipboard.isSupported()) {}
  828. },
  829. moveCamera: function(deltaX, deltaY, softAllowBoundPush=false) {
  830. deltaX = deltaX * 1.5;
  831. deltaY = deltaY * 1.5;
  832. if (!userTouch && is_touch_device) {
  833. return;
  834. }
  835. if (flagMobilePinch) {
  836. return;
  837. }
  838. if (!userIsDraw) {
  839. var cam = $(this.cameraController);
  840. var zoomModifier = this._getCurrentZoom();
  841. var coords = this.getCoordinates();
  842. var x = deltaX / zoomModifier
  843. , y = deltaY / zoomModifier;
  844. this.setCanvasPosition(x, y, true, softAllowBoundPush);
  845. }
  846. },
  847. updateCoordinates: function() {
  848. var coord = this.getCoordinates();
  849. if (coord != this.lastUpdatedCoordinates) {
  850. var coordElem = $(this.coordinateElement);
  851. setTimeout(function() {
  852. var spans = coordElem.find("span");
  853. spans.first().text(coord.x.toLocaleString());
  854. spans.last().text(coord.y.toLocaleString());
  855. coordElem.attr("data-clipboard-text", `(${coord.x}, ${coord.y})`);
  856. }, 0);
  857. }
  858. this.lastUpdatedCoordinates = coord;
  859. if (user.curentPage == 2) {
  860. $("#vkHeaderText").text("x: " + parseInt(coord.x) + " y: " + coord.y);
  861. }
  862. },
  863. isOutsideOfBounds: function(precise=false) {
  864. var coord = this.getCoordinates();
  865. var x = coord.x < 0 || coord.x >= place.canvas.width
  866. , y = coord.y >= size || coord.y < 0
  867. return precise ? {
  868. x: x,
  869. y: y
  870. } : x || y;
  871. },
  872. getCoordinates: function() {
  873. var dcanvas = this.canvasController.canvas;
  874. return {
  875. x: Math.floor(-this.panX) + dcanvas.width / 2,
  876. y: Math.floor(-this.panY) + dcanvas.height / 2
  877. };
  878. },
  879. setCanvasPosition: function(x, y, delta=false, softAllowBoundPush=true) {
  880. lastMove = Date.now();
  881. if (is_touch_device) {
  882. $(place.grid).removeClass("show");
  883. }
  884. $(this.pixelDataPopover).hide();
  885. if (delta)
  886. this.panX += x,
  887. this.panY += y;
  888. else
  889. this.panX = x,
  890. this.panY = y;
  891. if (!softAllowBoundPush) {
  892. this.panX = Math.max(-(place.canvas.width / 2) + 1, Math.min((place.canvas.width / 2), this.panX));
  893. this.panY = Math.max(-(size / 2) + 1, Math.min((size / 2), this.panY));
  894. }
  895. $(this.cameraController).css({
  896. top: `${this.panY}px`,
  897. left: `${this.panX}px`
  898. })
  899. this.updateGrid();
  900. if (this.lastX,
  901. this.lastY)
  902. this.updateGridHint(this.lastX, this.lastY);
  903. if (this.lastX,
  904. this.lastY)
  905. this.updateStencil();
  906. this.updateCoordinates();
  907. this.updateDisplayCanvas();
  908. },
  909. updateGrid: function() {
  910. var zoom = this._getCurrentZoom();
  911. var x = ($(this.cameraController).offset().left - (zoom / 2)) % zoom;
  912. var y = ($(this.cameraController).offset().top - (zoom / 2)) % zoom;
  913. $(this.grid).css({
  914. transform: `translate(${x}px, ${y}px)`,
  915. backgroundSize: `${zoom}px ${zoom}px`
  916. });
  917. },
  918. toggleGrid: function() {
  919. $(this.grid).toggleClass("show");
  920. this._adjustGridButtonText();
  921. },
  922. updateGridHint: function(x, y) {},
  923. updateStencil: function() {
  924. this.updateRedzone();
  925. this.setStencil(stencil.x, stencil.y);
  926. if (stencil.isVisible) {
  927. $(stencil.stencilDiv).css({
  928. width: ((1 * place._getZoomMultiplier()) * stencil.width) + "px",
  929. height: ((1 * place._getZoomMultiplier()) * stencil.height) + "px"
  930. });
  931. }
  932. },
  933. updateRedzone: function() {
  934. if (user.room == 1) {
  935. $(stencil.redZoneDiv).css('box-shadow', '0px 0px ' + (1 * place._getZoomMultiplier()) * 10 + 'px 0px rgb(255, 0, 0)');
  936. $(stencil.redZoneDiv).css('border', (1 * place._getZoomMultiplier()) * 2 + 'px solid red');
  937. this.setRedzone(place.canvas.width / 2 - 100, place.canvas.height / 2 - 100);
  938. $(stencil.redZoneDiv).css({
  939. width: ((1 * place._getZoomMultiplier()) * (100 * 2 + 1)) + "px",
  940. height: ((1 * place._getZoomMultiplier()) * (100 * 2 + 1)) + "px"
  941. });
  942. }
  943. },
  944. setStencil: function(x, y) {
  945. x = $(place.cameraController).offset().left + (x * place._getZoomMultiplier());
  946. y = $(place.cameraController).offset().top + (y * place._getZoomMultiplier());
  947. this.lastX = x;
  948. this.lastY = y;
  949. if (stencil.stencilDiv) {
  950. var zoom = this._getCurrentZoom();
  951. var x = Math.round((this.lastX - $(this.cameraController).offset().left) / zoom)
  952. , y = Math.round((this.lastY - $(this.cameraController).offset().top) / zoom);
  953. var elem = $(stencil.stencilDiv);
  954. var posX = x + ($(this.cameraController).offset().left / zoom) - 0.5;
  955. var posY = y + ($(this.cameraController).offset().top / zoom) - 0.5;
  956. elem.css({
  957. left: posX * zoom,
  958. top: posY * zoom,
  959. });
  960. }
  961. },
  962. setRedzone: function(x, y) {
  963. x = $(place.cameraController).offset().left + (x * place._getZoomMultiplier());
  964. y = $(place.cameraController).offset().top + (y * place._getZoomMultiplier());
  965. this.lastX = x;
  966. this.lastY = y;
  967. if (stencil.redZoneDiv) {
  968. var zoom = this._getCurrentZoom();
  969. var x = Math.round((this.lastX - $(this.cameraController).offset().left) / zoom)
  970. , y = Math.round((this.lastY - $(this.cameraController).offset().top) / zoom);
  971. var elem = $(stencil.redZoneDiv);
  972. var posX = x + ($(this.cameraController).offset().left / zoom) - 0.5;
  973. var posY = y + ($(this.cameraController).offset().top / zoom) - 0.5;
  974. elem.css({
  975. left: posX * zoom,
  976. top: posY * zoom,
  977. });
  978. }
  979. },
  980. setGridHint: function(x, y) {
  981. x = $(place.cameraController).offset().left + (x * place._getZoomMultiplier()) - (1 * place._getZoomMultiplier());
  982. y = $(place.cameraController).offset().top + (y * place._getZoomMultiplier()) - (1 * place._getZoomMultiplier());
  983. this.lastX = x;
  984. this.lastY = y;
  985. if (this.gridHint) {
  986. var zoom = this._getCurrentZoom();
  987. var x = Math.round((this.lastX - $(this.cameraController).offset().left) / zoom)
  988. , y = Math.round((this.lastY - $(this.cameraController).offset().top) / zoom);
  989. var elem = $(this.gridHint);
  990. var posX = x + ($(this.cameraController).offset().left / zoom) - 0.5;
  991. var posY = y + ($(this.cameraController).offset().top / zoom) - 0.5;
  992. elem.css({
  993. left: posX * zoom,
  994. top: posY * zoom,
  995. });
  996. }
  997. },
  998. handleMouseMove: function(event) {
  999. if (!this.placing) {
  1000. this.updateGridHint(event.pageX, event.pageY);
  1001. this.updateStencil();
  1002. if (this.handElement) {
  1003. var elem = $(this.handElement);
  1004. elem.css({
  1005. left: event.pageX - (elem.width() / 2),
  1006. top: event.pageY - (elem.height() / 2),
  1007. });
  1008. }
  1009. }
  1010. },
  1011. closestInsideCoordinates: function(x, y) {
  1012. return {
  1013. x: Math.max(0, Math.min(x, place.canvas.width - 1)),
  1014. y: Math.max(0, Math.min(y, size - 1))
  1015. };
  1016. },
  1017. contextMenu: function(event) {
  1018. event.preventDefault();
  1019. },
  1020. getPixel: function(x, y, callback) {},
  1021. isSignedIn: function() {
  1022. return $("body").hasClass("signed-in");
  1023. },
  1024. updatePlaceTimer: function() {
  1025. if (this.isSignedIn()) {
  1026. this.changePlaceTimerVisibility(true);
  1027. $(this.placeTimer).children("span").text("Loading…");
  1028. var a = this;
  1029. return placeAjax.get("/api/timer").then((data)=>a.doTimer(data.timer)).catch((err)=>this.changePlaceTimerVisibility(false));
  1030. }
  1031. this.changePlaceTimerVisibility(false);
  1032. },
  1033. doTimer: function(data) {
  1034. this.changePlaceTimerVisibility(true);
  1035. if (data.canPlace)
  1036. return this.changePlaceTimerVisibility(false);
  1037. this.unlockTime = (new Date().getTime() / 1000) + data.seconds;
  1038. this.fullUnlockTime = data.seconds;
  1039. this.secondTimer = setInterval(()=>this.checkSecondsTimer(), 1000);
  1040. this.checkSecondsTimer();
  1041. },
  1042. getSiteName: function() {
  1043. return $("meta[name=place-site-name]").attr("content");
  1044. },
  1045. checkSecondsTimer: function() {
  1046. function padLeft(str, pad, length) {
  1047. if (str.length > length)
  1048. return str;
  1049. return (new Array(length + 1).join(pad) + str).slice(-length);
  1050. }
  1051. if (this.unlockTime && this.secondTimer && this.fullUnlockTime) {
  1052. var time = Math.round(this.unlockTime - new Date().getTime() / 1000);
  1053. if (time > 0) {
  1054. var minutes = ~~(time / 60)
  1055. , seconds = time - minutes * 60;
  1056. var formattedTime = `${minutes}:${padLeft(seconds.toString(), "0", 2)}`;
  1057. document.title = `[${formattedTime}] | ${this.originalTitle}`;
  1058. var shouldShowNotifyButton = !this.notificationHandler.canNotify() && this.notificationHandler.isAbleToRequestPermission();
  1059. $(this.placeTimer).children("span").html("You may place again in <strong>" + formattedTime + "</strong>." + (shouldShowNotifyButton ? " <a href=\"#\" id=\"notify-me\">Notify me</a>." : ""));
  1060. return;
  1061. } else if (this.fullUnlockTime > 5) {
  1062. this.notificationHandler.sendNotification(this.getSiteName(), "You may now place!");
  1063. }
  1064. }
  1065. if (this.secondTimer)
  1066. clearInterval(this.secondTimer);
  1067. this.secondTimer = null,
  1068. this.unlockTime = null,
  1069. this.fullUnlockTime = null;
  1070. document.title = this.originalTitle;
  1071. this.changePlaceTimerVisibility(false);
  1072. },
  1073. handleNotifyMeClick: function() {
  1074. if (!this.notificationHandler.canNotify() && this.notificationHandler.isAbleToRequestPermission())
  1075. return this.notificationHandler.requestPermission((success)=>this.checkSecondsTimer());
  1076. this.checkSecondsTimer();
  1077. },
  1078. changeUserCount: function(newContent) {
  1079. var elem = $(this.userCountElement);
  1080. elem.show();
  1081. var notch = elem.find(".loading");
  1082. var text = elem.find(".count");
  1083. var num = parseInt(newContent);
  1084. if (num === null || isNaN(num)) {
  1085. notch.show();
  1086. text.text("");
  1087. } else {
  1088. notch.hide();
  1089. text.text(num.toLocaleString());
  1090. }
  1091. },
  1092. changePlaceTimerVisibility: function(visible) {
  1093. if (visible)
  1094. $(this.placeTimer).addClass("shown");
  1095. else
  1096. $(this.placeTimer).removeClass("shown");
  1097. this.changeSelectorVisibility(!visible);
  1098. },
  1099. changePlacingModalVisibility: function(visible) {
  1100. if (visible)
  1101. $(this.placingOverlay).addClass("shown");
  1102. else
  1103. $(this.placingOverlay).removeClass("shown");
  1104. },
  1105. selectColour: function(colourID, hideColourPicker=true) {
  1106. var hasSelectedColor = this.colourPaletteOptionElements[colourID - 1].classList.contains('selected');
  1107. this.deselectColour(hideColourPicker);
  1108. if (hasSelectedColor == false) {
  1109. this.selectedColour = colourID - 1;
  1110. var elem = this.colourPaletteOptionElements[this.selectedColour];
  1111. this.handElement = $(elem).clone().addClass("hand").appendTo($(this.zoomController).parent())[0];
  1112. this.updateUIWithZoomScale();
  1113. $(elem).addClass("selected");
  1114. $(this.zoomController).addClass("selected");
  1115. if (this.lastX && this.lastY)
  1116. this.updateGridHint(this.lastX, this.lastY);
  1117. }
  1118. },
  1119. deselectColour: function(hideColourPicker=true) {
  1120. this.selectedColour = null;
  1121. if (hideColourPicker)
  1122. $("body").removeClass("picker-showing");
  1123. $(this.handElement).remove();
  1124. $(this.colourPaletteOptionElements).removeClass("selected");
  1125. $(this.zoomController).removeClass("selected");
  1126. },
  1127. changeSelectorVisibility: function(visible) {
  1128. if (this.selectedColour == null)
  1129. return;
  1130. if (visible) {
  1131. var elem = this.colourPaletteOptionElements[this.selectedColour];
  1132. $(this.handElement).show();
  1133. $(this.zoomController).addClass("selected");
  1134. } else {
  1135. $(this.handElement).hide();
  1136. $(this.zoomController).removeClass("selected");
  1137. }
  1138. },
  1139. zoomIntoPoint: function(x, y, actuallyZoom=true) {
  1140. this.zooming.panToX = -(x - place.canvas.width / 2);
  1141. this.zooming.panToY = -(y - size / 2);
  1142. this.zooming.panFromX = this.panX;
  1143. this.zooming.panFromY = this.panY;
  1144. this.setZoomScale(actuallyZoom && !this.zooming.zoomedIn ? 40 : this.zooming.zoomScale, true);
  1145. },
  1146. protection: function() {
  1147. if (place._protection){
  1148. var editt = 0;
  1149. var counterr = 920;
  1150. if(stencil.isVisible && stencil.isPin && !stencil.opacity){
  1151. /*for (var x = stencil.x; x < (stencil.width + stencil.x); x++){
  1152. for (var y = stencil.y; y < (stencil.height + stencil.y); y++){
  1153. var CanX = x - stencil.x;
  1154. var CanY = y - stencil.y;
  1155.  
  1156. var hexColor = getPixelFromCanvas(ctxRender, CanX, CanY);
  1157. if(hexColor == "000000"){
  1158. hexColor = "222222"
  1159. }
  1160. //console.log(hexColor);
  1161. if(hexColor != 0){
  1162. var errorColor = {color:-1, score: 99999999};
  1163. for(var i = 0; i < place.colours.length; i++){
  1164. var tempScore = deltaE(hexToRgbArray("#" + hexColor), hexToRgbArray(place.colours[i]));
  1165. if(tempScore < errorColor.score){
  1166. errorColor.color = i + 1;
  1167. errorColor.score = tempScore;
  1168. }
  1169. }
  1170. } else {
  1171. if(place.selectedColour != 1){
  1172. place.selectColour(1 + 1);
  1173. }
  1174. }
  1175. var tess = canvasController.getPixelColour(x,y).toLowerCase();
  1176. var trueC = {color:-1, score: 99999999};
  1177. for(var i = 0; i < place.colours.length; i++){
  1178. var tempScoree = deltaE(hexToRgbArray("#" + tess), hexToRgbArray(place.colours[i]));
  1179. if(tempScoree < trueC.score){
  1180. trueC.color = i + 1;
  1181. trueC.score = tempScoree;
  1182. }
  1183. }
  1184. if(trueC.color != errorColor.color){
  1185. console.log("Found mistake at: "+x+" y:"+y);
  1186.  
  1187. if (place.placingOverlay.context.innerText.includes("пик") && (counterr>=0)){
  1188. counterr--;
  1189. console.log("Fixing...");
  1190. place.canvasClicked(x,y);
  1191.  
  1192. } else {
  1193. break;
  1194. }
  1195. }
  1196. }
  1197. }*/
  1198. while (counterr>0){
  1199. var millisecondsToWait = 500 + randomInteger(50,500);
  1200. setTimeout(function() {
  1201. var flag = true;
  1202. while (flag) {
  1203. var x = randomInteger(stencil.x, stencil.width+stencil.x);
  1204. var y = randomInteger(stencil.y, stencil.height+stencil.y);
  1205. var hexColor = getPixelFromCanvas(ctxRender, x, y);
  1206. if(hexColor == "000000"){
  1207. hexColor = "222222"
  1208. }
  1209. //console.log(hexColor);
  1210. if(hexColor != 0){
  1211. var errorColor = {color:-1, score: 99999999};
  1212. for(var i = 0; i < place.colours.length; i++){
  1213. var tempScore = deltaE(hexToRgbArray("#" + hexColor), hexToRgbArray(place.colours[i]));
  1214. if(tempScore < errorColor.score){
  1215. errorColor.color = i + 1;
  1216. errorColor.score = tempScore;
  1217. }
  1218. }
  1219. } else {
  1220. if(place.selectedColour != 1){
  1221. place.selectColour(1 + 1);
  1222. }
  1223. }
  1224. var tess = canvasController.getPixelColour(x,y).toLowerCase();
  1225. var trueC = {color:-1, score: 99999999};
  1226. for(var i = 0; i < place.colours.length; i++){
  1227. var tempScoree = deltaE(hexToRgbArray("#" + tess), hexToRgbArray(place.colours[i]));
  1228. if(tempScoree < trueC.score){
  1229. trueC.color = i + 1;
  1230. trueC.score = tempScoree;
  1231. }
  1232. }
  1233. if(trueC.color != errorColor.color){
  1234. flag = false;
  1235. place.canvasClicked(x,y);
  1236. }
  1237. }
  1238. }, millisecondsToWait);
  1239.  
  1240.  
  1241. counterr--;
  1242. }
  1243. }
  1244. } else {
  1245. console.log("NO");
  1246. }
  1247. },
  1248. canvasClicked: function(x, y, event) {
  1249. if (flagMobilePinch) {
  1250. return;
  1251. }
  1252. if (stencil.isVisible && !stencil.isPin) {
  1253. stencil.x = x;
  1254. stencil.y = y;
  1255. place.updateStencil();
  1256. stencil.saveStencilSettings();
  1257. return;
  1258. }
  1259. if (user.room == 3) {
  1260. console.log(x, y);
  1261. if (x == 284 && y == 26) {
  1262. openModal("modal2128");
  1263. return;
  1264. }
  1265. }
  1266. var stencilHexColor = "";
  1267. if (stencil.isVisible && stencil.isPin && !stencil.opacity) {
  1268. if (x >= stencil.x && x < stencil.width + stencil.x && y >= stencil.y && y < stencil.height + stencil.y) {
  1269. var coordClickCanvasX = x - stencil.x;
  1270. var coordClickCanvasY = y - stencil.y;
  1271. var hexColor = getPixelFromCanvas(ctxRender, coordClickCanvasX, coordClickCanvasY);
  1272. if (hexColor == "000000") {
  1273. hexColor = "222222"
  1274. }
  1275. if (hexColor != 0) {
  1276. var errorColor = {
  1277. color: -1,
  1278. score: 99999999
  1279. };
  1280. for (var i = 0; i < place.colours.length; i++) {
  1281. var tempScore = deltaE(hexToRgbArray("#" + hexColor), hexToRgbArray(place.colours[i]));
  1282. if (tempScore < errorColor.score) {
  1283. errorColor.color = i + 1;
  1284. errorColor.score = tempScore;
  1285. }
  1286. }
  1287. if (place.selectedColour != errorColor.color) {
  1288. place.selectColour(errorColor.color + 1);
  1289. }
  1290. } else {
  1291. if (place.selectedColour != 1) {
  1292. place.selectColour(1 + 1);
  1293. }
  1294. }
  1295. if (user.crafted.pixelgun_gold == 1 || user.crafted.pixelgun == 4) {
  1296. stencilHexColor = hexColor;
  1297. if (place.selectedColour != 1) {
  1298. place.selectColour(2);
  1299. }
  1300. }
  1301. } else {
  1302. if (stencil.userStartDrawHoldOnStencil == true) {
  1303. return;
  1304. }
  1305. }
  1306. }
  1307. var app = this;
  1308. this.stat();
  1309. function getUserInfoTableItem(title, value) {
  1310. var ctn = $("<div>").addClass("field");
  1311. $("<span>").addClass("title").text(title).appendTo(ctn);
  1312. $(`<span>`).addClass("value").html(value).appendTo(ctn);
  1313. return ctn;
  1314. }
  1315. function getUserInfoDateTableItem(title, date) {
  1316. var ctn = getUserInfoTableItem(title, "");
  1317. $("<time>").attr("datetime", date).attr("title", new Date(date).toLocaleString()).text($.timeago(date)).prependTo(ctn.find(".value"));
  1318. return ctn;
  1319. }
  1320. $(this.pixelDataPopover).hide();
  1321. if (x < 0 || y < 0 || x > place.canvas.width - 1 || y > this.canvas.height - 1)
  1322. return;
  1323. var wasZoomedOut = !this.zooming.zoomedIn;
  1324. if (wasZoomedOut)
  1325. this.zoomIntoPoint(x, y);
  1326. if (this.selectedColour === null) {
  1327. this.zoomIntoPoint(x, y, false);
  1328. $("#loading_pixel").show();
  1329. $.ajaxq('MyQueueGetPixel' + randomIntFromInterval(1, 1000), {
  1330. type: 'POST',
  1331. url: 'api.php?te=1',
  1332. data: {
  1333. user_id: user.user_id,
  1334. token: user.token,
  1335. getinfo: 1,
  1336. x: x,
  1337. y: y
  1338. },
  1339. success: function(returnedData) {
  1340. returnedData = JSON.parse(returnedData);
  1341. if (returnedData.placed_by_real > 0) {
  1342. $("#usercolor").show();
  1343. if (returnedData.color_team != 0) {
  1344. document.getElementById("usercolor").style.color = returnedData.color_team;
  1345. } else {
  1346. document.getElementById("usercolor").style.color = "#F8F9FD";
  1347. }
  1348. document.getElementById("pixel-data-username").style.color = "#368bd9";
  1349. document.getElementById("pixel-data-username").href = "https://vk.com/id" + parseInt(returnedData.placed_by_real);
  1350. document.getElementById("pixel-data-username").onclick = function() {
  1351. openLink("https://vk.com/id" + parseInt(returnedData.placed_by_real));
  1352. }
  1353. var req = "https://api.vk.com/method/users.get?access_token=2ed67e9b2ed67e9b2ed67e9bcd2ebc9a1d22ed62ed67e9b72243844742df4e756c3ef41&fields=photo_200&v=5.80&lang=ru&user_ids=" + returnedData.placed_by_real;
  1354. $.ajax({
  1355. url: req,
  1356. type: "GET",
  1357. dataType: "jsonp",
  1358. success: function(msgMain) {
  1359. var nameText = (msgMain.response[0].first_name[0] + ". " + " " + msgMain.response[0].last_name);
  1360. if (nameText.length > 14) {
  1361. nameText = nameText.slice(0, 12) + "...";
  1362. }
  1363. $("#pixel-data-username").text(strip_tags(nameText));
  1364. if (returnedData.placed_by < 0) {
  1365. document.getElementById("pixel-data-username").style.float = "left";
  1366. $("#pixel-data-username").html('<i id="userico" class="fas fa-user"></i> ' + $("#pixel-data-username").text());
  1367. document.getElementById("pixel-data-clan").style.color = "#368bd9";
  1368. document.getElementById("pixel-data-clan").href = "https://vk.com/public" + Math.abs(parseInt(returnedData.placed_by));
  1369. document.getElementById("pixel-data-clan").onclick = function() {
  1370. openLink("https://vk.com/public" + Math.abs(parseInt(returnedData.placed_by)));
  1371. }
  1372. var req = "https://api.vk.com/method/groups.getById?access_token=2ed67e9b2ed67e9b2ed67e9bcd2ebc9a1d22ed62ed67e9b72243844742df4e756c3ef41&fields=photo_200&v=5.80&lang=ru&group_ids=" + Math.abs(returnedData.placed_by);
  1373. $.ajax({
  1374. url: req,
  1375. type: "GET",
  1376. dataType: "jsonp",
  1377. success: function(msgMain) {
  1378. var nameText = strip_tags((msgMain.response[0].name));
  1379. if (nameText.length > 14) {
  1380. nameText = nameText.slice(0, 12) + "...";
  1381. }
  1382. $("#pixel-data-clan").text(nameText);
  1383. $("#loading_pixel").hide();
  1384. }
  1385. });
  1386. $(".userclan").show();
  1387. $("#loading_pixel").hide();
  1388. } else {
  1389. document.getElementById("pixel-data-username").style.float = "none";
  1390. document.getElementById("pixel-data-clan").style.color = "black";
  1391. document.getElementById("pixel-data-clan").onclick = function() {}
  1392. $("#loading_pixel").hide();
  1393. $(".userclan").hide();
  1394. }
  1395. }
  1396. });
  1397. } else {
  1398. $("#usercolor").hide();
  1399. $(".userclan").hide();
  1400. $("#pixel-data-username").text("Пиксель пуст");
  1401. document.getElementById("pixel-data-username").style.color = "black";
  1402. document.getElementById("pixel-data-username").onclick = function() {}
  1403. $("#loading_pixel").hide();
  1404. }
  1405. if (parseInt(returnedData.placed_by) > 0) {} else {}
  1406. }
  1407. });
  1408. lastClickedInfo.x = x;
  1409. lastClickedInfo.y = y;
  1410. $(".username-container").show();
  1411. $(".intro").show();
  1412. var popover = $(this.pixelDataPopover);
  1413. if (this.zooming.zooming)
  1414. this.shouldShowPopover = true;
  1415. else
  1416. popover.fadeIn(250);
  1417. popover.find("#pixel-data-x").text(x.toLocaleString());
  1418. popover.find("#pixel-data-y").text(y.toLocaleString());
  1419. return this.getPixel(x, y, (err,data)=>{
  1420. if (err || !data.pixel)
  1421. return;
  1422. var popover = $(this.pixelDataPopover);
  1423. if (this.zooming.zooming)
  1424. this.shouldShowPopover = true;
  1425. else
  1426. popover.fadeIn(250);
  1427. var hasUser = !!data.pixel.user;
  1428. if (typeof data.pixel.userError === "undefined")
  1429. data.pixel.userError = null;
  1430. popover.find("#pixel-data-username").text(hasUser ? data.pixel.user.username : this.getUserStateText(data.pixel.userError));
  1431. if (hasUser)
  1432. popover.find("#pixel-data-username").removeClass("deleted-account");
  1433. else
  1434. popover.find("#pixel-data-username").addClass("deleted-account");
  1435. popover.find("#pixel-data-time").text($.timeago(data.pixel.modified));
  1436. popover.find("#pixel-data-time").attr("datetime", data.pixel.modified);
  1437. popover.find("#pixel-data-time").attr("title", new Date(data.pixel.modified).toLocaleString());
  1438. popover.find("#pixel-data-x").text(x.toLocaleString());
  1439. popover.find("#pixel-data-y").text(y.toLocaleString());
  1440. popover.find("#pixel-colour-code").text(`#${data.pixel.colour.toUpperCase()}`);
  1441. popover.find("#pixel-colour-preview").css("background-color", `#${data.pixel.colour}`);
  1442. if (data.pixel.colour.toLowerCase() == "ffffff")
  1443. popover.find("#pixel-colour-preview").addClass("is-white");
  1444. else
  1445. popover.find("#pixel-colour-preview").removeClass("is-white");
  1446. popover.find("#pixel-use-colour-btn").attr("data-represented-colour", data.pixel.colour);
  1447. if (this.canPlaceCustomColours)
  1448. popover.find(".pixel-colour").addClass("allow-use");
  1449. else
  1450. popover.find(".pixel-colour").removeClass("allow-use");
  1451. popover.find(".rank-container > *").remove();
  1452. if (hasUser) {
  1453. var userInfoCtn = popover.find(".user-info");
  1454. userInfoCtn.show();
  1455. userInfoCtn.find(".field").remove();
  1456. getUserInfoTableItem("Total pixels placed", data.pixel.user.statistics.totalPlaces.toLocaleString()).appendTo(userInfoCtn);
  1457. if (data.pixel.user.statistics.placesThisWeek !== null)
  1458. getUserInfoTableItem("Pixels this week", data.pixel.user.statistics.placesThisWeek.toLocaleString()).appendTo(userInfoCtn);
  1459. getUserInfoDateTableItem("Account created", data.pixel.user.creationDate).appendTo(userInfoCtn);
  1460. var latestCtn = getUserInfoDateTableItem("Last placed", data.pixel.user.statistics.lastPlace).appendTo(userInfoCtn);
  1461. if (data.pixel.user.latestPixel && data.pixel.user.latestPixel.isLatest) {
  1462. var latest = data.pixel.user.latestPixel;
  1463. var element = $("<div>")
  1464. if (data.pixel.point.x == latest.point.x && data.pixel.point.y == latest.point.y)
  1465. $("<span>").addClass("secondary-info").text("(this pixel)").appendTo(element);
  1466. else
  1467. $("<a>").attr("href", "javascript:void(0)").text(`at (${latest.point.x.toLocaleString()}, ${latest.point.y.toLocaleString()})`).click(()=>app.zoomIntoPoint(latest.point.x, latest.point.y, false)).appendTo(element);
  1468. element.appendTo(latestCtn.find(".value"));
  1469. }
  1470. popover.find("#pixel-data-username").attr("href", `/@${data.pixel.user.username}`);
  1471. var rankContainer = popover.find(".rank-container");
  1472. data.pixel.user.badges.forEach((badge)=>renderBadge(badge).appendTo(rankContainer));
  1473. popover.find("#user-actions-dropdown-ctn").html(renderUserActionsDropdown(data.pixel.user));
  1474. } else {
  1475. popover.find(".user-info, #pixel-badge, #pixel-user-state-badge").hide();
  1476. popover.find("#user-actions-dropdown-ctn").html("");
  1477. popover.find("#pixel-data-username").removeAttr("href");
  1478. }
  1479. }
  1480. );
  1481. }
  1482. if (wasZoomedOut)
  1483. return;
  1484. if ((this.selectedColour !== null && !this.placing) || user.bomb != 0) {
  1485. var hex = this.getCurrentColourHex();
  1486. if (user.pixels[hexToColorID(hex)] > 0 || user.crafted.pixelgun > -1 || user.crafted.pixelgun_gold == 1) {
  1487. if (user.room == 1) {
  1488. if (("#" + canvasController.getPixelColour(x, y)).toLowerCase() != hex.toLowerCase() || stencilHexColor != "") {
  1489. var oldColor = "#" + canvasController.getPixelColour(x, y);
  1490. if (user.user_id != 1) {
  1491. var objEmit = null;
  1492. if ((user.crafted.pixelgun_gold == 1 || user.crafted.pixelgun == 4) && stencilHexColor != "") {
  1493. if ((canvasController.getPixelColour(x, y)).toLowerCase() != stencilHexColor.toLowerCase()) {
  1494. var objEmit = {
  1495. "user_id": user.user_id,
  1496. "token": user.token,
  1497. "x": x,
  1498. "y": y,
  1499. "color": stencilHexColor,
  1500. }
  1501. place.placing = true;
  1502. place.setPixel(stencilHexColor, x, y);
  1503. place.placing = false;
  1504. }
  1505. } else {
  1506. var objEmit = {
  1507. "user_id": user.user_id,
  1508. "token": user.token,
  1509. "x": x,
  1510. "y": y,
  1511. "color": hexToColorID(hex),
  1512. }
  1513. place.placing = true;
  1514. place.setPixel(hex, x, y);
  1515. place.placing = false;
  1516. }
  1517. $.ajaxq('MyQueue1' + randomIntFromInterval(1, 1000), {
  1518. type: 'POST',
  1519. url: 'api.php?te=1',
  1520. data: {
  1521. user_id: user.id,
  1522. token: user.token,
  1523. draw: 1,
  1524. datasocket: JSON.stringify(objEmit)
  1525. },
  1526. success: function(returnedData) {
  1527. if (returnedData != "ok" && returnedData != "error") {
  1528. place.placing = true;
  1529. place.setPixel(oldColor, x, y);
  1530. place.placing = false;
  1531. showNotify(returnedData, 1500);
  1532. }
  1533. }
  1534. });
  1535. if (user.tutorials["collect_for_pixelgun"] == 0) {
  1536. user.tutorials["collect_for_pixelgun"] = 1;
  1537. setTimeout(function() {
  1538. openModal("modal" + "collect_for_pixelgun");
  1539. }, 3000);
  1540. }
  1541. } else {
  1542. if ((user.crafted.pixelgun_gold == 1 || user.crafted.pixelgun == 4) && stencilHexColor != "") {
  1543. if ((canvasController.getPixelColour(x, y)).toLowerCase() != stencilHexColor.toLowerCase()) {
  1544. var _0xd328 = ["\x75\x73\x65\x72\x5F\x69\x64", "\x74\x6F\x6B\x65\x6E", "\x64\x72\x61\x77", "\x73\x74\x72\x69\x6E\x67\x69\x66\x79", "\x65\x6D\x69\x74"];
  1545. var objEmit = {
  1546. "\x75\x73\x65\x72\x5F\x69\x64": user[_0xd328[0]],
  1547. "\x74\x6F\x6B\x65\x6E": user[_0xd328[1]],
  1548. "\x78": x,
  1549. "\x79": y,
  1550. "\x63\x6F\x6C\x6F\x72": stencilHexColor,
  1551. "\x6B\x65\x79": mycolor
  1552. };
  1553. socket[_0xd328[4]](_0xd328[2], JSON[_0xd328[3]](objEmit));
  1554. }
  1555. } else {
  1556. var _0xd328 = ["\x75\x73\x65\x72\x5F\x69\x64", "\x74\x6F\x6B\x65\x6E", "\x64\x72\x61\x77", "\x73\x74\x72\x69\x6E\x67\x69\x66\x79", "\x65\x6D\x69\x74"];
  1557. var objEmit = {
  1558. "\x75\x73\x65\x72\x5F\x69\x64": user[_0xd328[0]],
  1559. "\x74\x6F\x6B\x65\x6E": user[_0xd328[1]],
  1560. "\x78": x,
  1561. "\x79": y,
  1562. "\x63\x6F\x6C\x6F\x72": hexToColorID(hex),
  1563. "\x6B\x65\x79": mycolor
  1564. };
  1565. socket[_0xd328[4]](_0xd328[2], JSON[_0xd328[3]](objEmit));
  1566. }
  1567. if (user.tutorials["collect_for_pixelgun"] == 0) {
  1568. user.tutorials["collect_for_pixelgun"] = 1;
  1569. setTimeout(function() {
  1570. openModal("modal" + "collect_for_pixelgun");
  1571. }, 2000);
  1572. }
  1573. }
  1574. }
  1575. }
  1576. if (user.room == 2) {
  1577. if (("#" + canvasController.getPixelColour(x, y)).toLowerCase() != hex.toLowerCase() || stencilHexColor != "") {
  1578. if ((user.crafted.pixelgun_gold == 1 || user.crafted.pixelgun == 4) && stencilHexColor != "") {
  1579. if ((canvasController.getPixelColour(x, y)).toLowerCase() != stencilHexColor.toLowerCase()) {
  1580. var _0xdda1 = ["\x75\x73\x65\x72\x5F\x69\x64", "\x74\x6F\x6B\x65\x6E", "\x64\x72\x61\x77", "\x73\x74\x72\x69\x6E\x67\x69\x66\x79", "\x65\x6D\x69\x74"];
  1581. var objEmit = {
  1582. "\x75\x73\x65\x72\x5F\x69\x64": user[_0xdda1[0]],
  1583. "\x74\x6F\x6B\x65\x6E": user[_0xdda1[1]],
  1584. "\x78": x,
  1585. "\x79": y,
  1586. "\x63\x6F\x6C\x6F\x72": stencilHexColor,
  1587. "\x6B\x65\x79": mycolor
  1588. };
  1589. socket[_0xdda1[4]](_0xdda1[2], JSON[_0xdda1[3]](objEmit));
  1590. }
  1591. } else {
  1592. var _0xdda1 = ["\x75\x73\x65\x72\x5F\x69\x64", "\x74\x6F\x6B\x65\x6E", "\x64\x72\x61\x77", "\x73\x74\x72\x69\x6E\x67\x69\x66\x79", "\x65\x6D\x69\x74"];
  1593. var objEmit = {
  1594. "\x75\x73\x65\x72\x5F\x69\x64": user[_0xdda1[0]],
  1595. "\x74\x6F\x6B\x65\x6E": user[_0xdda1[1]],
  1596. "\x78": x,
  1597. "\x79": y,
  1598. "\x63\x6F\x6C\x6F\x72": hexToColorID(hex),
  1599. "\x6B\x65\x79": mycolor
  1600. };
  1601. socket[_0xdda1[4]](_0xdda1[2], JSON[_0xdda1[3]](objEmit));
  1602. }
  1603. }
  1604. }
  1605. if (user.room == 3) {
  1606. if (user.user_id != 1) {
  1607. var objEmit = {
  1608. "user_id": user.user_id,
  1609. "token": user.token,
  1610. "x": x,
  1611. "y": y,
  1612. "color": hexToColorID(hex),
  1613. "bomb": user.bomb,
  1614. }
  1615. $.ajaxq('MyQueue3' + randomIntFromInterval(1, 1000), {
  1616. type: 'POST',
  1617. url: 'api.php?te=1',
  1618. data: {
  1619. user_id: user.id,
  1620. token: user.token,
  1621. draw3: 1,
  1622. datasocket: JSON.stringify(objEmit)
  1623. },
  1624. success: function(returnedData) {
  1625. if (returnedData != "ok" && returnedData != "error") {
  1626. showNotify(returnedData, 1500);
  1627. }
  1628. }
  1629. });
  1630. } else {
  1631. var objEmit = {
  1632. "user_id": user.user_id,
  1633. "token": user.token,
  1634. "x": x,
  1635. "y": y,
  1636. "color": hexToColorID(hex),
  1637. "bomb": user.bomb,
  1638. }
  1639. socket.emit('draw', JSON.stringify(objEmit));
  1640. }
  1641. }
  1642. if (user.room == 4) {
  1643. if (("#" + canvasController.getPixelColour(x, y)).toLowerCase() != hex.toLowerCase() || stencilHexColor != "") {
  1644. if ((user.crafted.pixelgun_gold == 1 || user.crafted.pixelgun == 4) && stencilHexColor != "") {
  1645. if ((canvasController.getPixelColour(x, y)).toLowerCase() != stencilHexColor.toLowerCase()) {
  1646. var _0xdda1 = ["\x75\x73\x65\x72\x5F\x69\x64", "\x74\x6F\x6B\x65\x6E", "\x64\x72\x61\x77", "\x73\x74\x72\x69\x6E\x67\x69\x66\x79", "\x65\x6D\x69\x74"];
  1647. var objEmit = {
  1648. "\x75\x73\x65\x72\x5F\x69\x64": user[_0xdda1[0]],
  1649. "\x74\x6F\x6B\x65\x6E": user[_0xdda1[1]],
  1650. "\x78": x,
  1651. "\x79": y,
  1652. "\x63\x6F\x6C\x6F\x72": stencilHexColor,
  1653. "\x6B\x65\x79": mycolor
  1654. };
  1655. socket[_0xdda1[4]](_0xdda1[2], JSON[_0xdda1[3]](objEmit));
  1656. }
  1657. } else {
  1658. var _0xdda1 = ["\x75\x73\x65\x72\x5F\x69\x64", "\x74\x6F\x6B\x65\x6E", "\x64\x72\x61\x77", "\x73\x74\x72\x69\x6E\x67\x69\x66\x79", "\x65\x6D\x69\x74"];
  1659. var objEmit = {
  1660. "\x75\x73\x65\x72\x5F\x69\x64": user[_0xdda1[0]],
  1661. "\x74\x6F\x6B\x65\x6E": user[_0xdda1[1]],
  1662. "\x78": x,
  1663. "\x79": y,
  1664. "\x63\x6F\x6C\x6F\x72": hexToColorID(hex),
  1665. "\x6B\x65\x79": mycolor
  1666. };
  1667. socket[_0xdda1[4]](_0xdda1[2], JSON[_0xdda1[3]](objEmit));
  1668. }
  1669. }
  1670. }
  1671. } else {
  1672. if (lastNotifyPixelRemove + 1 <= parseInt(curentTimestampSync / 1000)) {
  1673. lastNotifyPixelRemove = parseInt(curentTimestampSync / 1000);
  1674. showNotify('Недостаточно пикселей. Перейдите на ферму что бы вырастить еще', 1500);
  1675. }
  1676. }
  1677. }
  1678. },
  1679. getCurrentColourHex: function() {
  1680. if (this.selectedColour <= 0 && this.customColour)
  1681. return this.customColour;
  1682. return this.colours[this.selectedColour - 1];
  1683. },
  1684. setPixel: function(colour, x, y) {
  1685. this.canvasController.setPixel(colour, x, y);
  1686. this.updateDisplayCanvas();
  1687. },
  1688. doKeys: function() {
  1689. var keys = Object.keys(this.keys).filter((key)=>this.keys[key].filter((keyCode)=>this.keyStates[keyCode] === true).length > 0);
  1690. if (keys.indexOf("up") > -1)
  1691. this.moveCamera(0, 5, false);
  1692. if (keys.indexOf("down") > -1)
  1693. this.moveCamera(0, -5, false);
  1694. if (keys.indexOf("left") > -1)
  1695. this.moveCamera(5, 0, false);
  1696. if (keys.indexOf("right") > -1)
  1697. this.moveCamera(-5, 0, false);
  1698. },
  1699. handleKeyDown: function(keycode) {
  1700. if (keycode == 71) {
  1701. this.toggleGrid();
  1702. } else if (keycode == 32) {
  1703. this.toggleZoom();
  1704. } else if (keycode == 27 && this.selectedColour !== null) {} else if (keycode == 80) {
  1705. this.pickColourUnderCursor();
  1706. }
  1707. },
  1708. pickColourUnderCursor: function() {
  1709. if (!this.canPlaceCustomColours)
  1710. return;
  1711. var cursor = this.getCanvasCursorPosition();
  1712. var colour = this.canvasController.getPixelColour(cursor.x, cursor.y);
  1713. $("#colour-picker").minicolors("value", "#" + colour);
  1714. },
  1715. adjustLoadingScreen: function(text=null) {
  1716. if (text) {
  1717. $("#loading").show().find(".text").text(text);
  1718. } else {
  1719. $("#loading").fadeOut();
  1720. }
  1721. },
  1722. getUserStateText: function(userState) {
  1723. if (userState == "ban")
  1724. return "Banned user";
  1725. if (userState == "deactivated")
  1726. return "Deactivated user";
  1727. return "Deleted account";
  1728. },
  1729. showAdminBroadcast: function(title, message, style, timeout=0) {
  1730. var alert = $("<div>").addClass("floating-alert admin-alert alert alert-block alert-dismissable").addClass("alert-" + style).hide().prependTo($("#floating-alert-ctn"));
  1731. this.dismissBtn.clone().appendTo(alert);
  1732. var text = $("<p>").text(message).appendTo(alert);
  1733. if (title != null && title != "") {
  1734. $("<span>").text(" ").prependTo(text);
  1735. $("<strong>").text(title).prependTo(text);
  1736. }
  1737. alert.fadeIn(400, function() {
  1738. if (timeout > 0) {
  1739. setTimeout(function() {
  1740. alert.fadeOut(400, function() {
  1741. alert.remove();
  1742. });
  1743. }, timeout * 1000);
  1744. }
  1745. });
  1746. },
  1747. handlePaletteExpandoClick: function() {
  1748. var options = {
  1749. duration: 150,
  1750. queue: false
  1751. };
  1752. var expand = $(this).toggleClass("expanded").hasClass("expanded");
  1753. if (expand)
  1754. $("#menu-content-ctn").slideDown(options);
  1755. else
  1756. $("#menu-content-ctn").slideUp(options).fadeOut(options);
  1757. },
  1758. loadWarps: function() {
  1759. if (!this.isSignedIn())
  1760. return;
  1761. placeAjax.get("/api/warps", null, null).then((response)=>{
  1762. this.warps = response.warps;
  1763. this.layoutWarps();
  1764. }
  1765. ).catch((err)=>{
  1766. console.error("Couldn't load warps: " + err);
  1767. this.warps = null;
  1768. this.layoutWarps();
  1769. }
  1770. );
  1771. },
  1772. layoutWarps: function() {
  1773. var app = this;
  1774. function getWarpInfo(title=null, detail=null, clickHandler=null, deleteClickHandler=null, add=false) {
  1775. var warpInfo = $("<div>").addClass("warp-info");
  1776. if (title)
  1777. $("<span>").addClass("warp-title").text(title).appendTo(warpInfo);
  1778. if (detail)
  1779. $("<span>").addClass("warp-coordinates").text(detail).appendTo(warpInfo);
  1780. if (add)
  1781. warpInfo.addClass("add").attr("title", "Create a warp at the current position").append("<span class=\"warp-title\"><i class=\"fa fa-plus\"></i></span>");
  1782. else {
  1783. if (typeof deleteClickHandler === "function")
  1784. $("<div>").addClass("warp-delete").attr("title", `Delete warp '${title}'`).html("<i class=\"fa fa-minus fa-fw\"></i>").click(deleteClickHandler.bind(app, warpInfo)).appendTo(warpInfo);
  1785. warpInfo.attr("title", `Warp to '${title}'`)
  1786. }
  1787. if (clickHandler)
  1788. warpInfo.click(clickHandler.bind(app, warpInfo));
  1789. return warpInfo;
  1790. }
  1791. var warpsContainer = $("#warps-ctn");
  1792. if (!this.warps)
  1793. return warpsContainer.text("Couldn't load warps.");
  1794. warpsContainer.html("");
  1795. var warpInfoContainer = $("<div>").addClass("menu-section-content").appendTo($("<div>").addClass("menu-section-content-ctn").appendTo(warpsContainer));
  1796. getWarpInfo(null, null, this.addNewWarpClicked, null, true).appendTo(warpInfoContainer);
  1797. if (this.warps.length > 0) {
  1798. this.warps.forEach((warp)=>getWarpInfo(warp.name, `(${warp.location.x.toLocaleString()}, ${warp.location.y.toLocaleString()})`, ()=>this.zoomIntoPoint(warp.location.x, warp.location.y, false), this.deleteWarpClicked).attr("data-warp-id", warp.id).appendTo(warpInfoContainer));
  1799. } else {
  1800. warpInfoContainer.addClass("empty");
  1801. var explanation = $("<div>").addClass("warp-info explanation").appendTo(warpInfoContainer);
  1802. $("<span>").addClass("warp-title").text("Warps").appendTo(explanation);
  1803. $("<span>").addClass("warp-coordinates").text("Use warps to get around the canvas quickly. Save a position and warp to it later on.").appendTo(explanation);
  1804. }
  1805. },
  1806. addNewWarpClicked: function(elem, event, input=null) {
  1807. var warpTitle = window.prompt(`Enter a title for this warp (at current position):`, input || "");
  1808. if (!warpTitle || warpTitle.length <= 0)
  1809. return;
  1810. var pos = this.getCoordinates();
  1811. placeAjax.post("/api/warps", {
  1812. x: pos.x,
  1813. y: pos.y,
  1814. name: warpTitle
  1815. }, "An unknown error occurred while attempting to create your warp.").then((response)=>{
  1816. if (response.warp)
  1817. this.warps.unshift(response.warp);
  1818. this.layoutWarps();
  1819. }
  1820. ).catch((err)=>{
  1821. if (err.code == "validation")
  1822. this.addNewWarpClicked(elem, event, warpTitle);
  1823. }
  1824. );
  1825. },
  1826. deleteWarpClicked: function(elem, event) {
  1827. event.preventDefault();
  1828. event.stopPropagation();
  1829. if (elem.data("deleting") === true)
  1830. return;
  1831. if (!window.confirm("Are you sure you want to delete this warp?"))
  1832. return;
  1833. function setDeletingState(deleting) {
  1834. elem.data("deleting", deleting);
  1835. var icon = elem.find("i");
  1836. if (deleting)
  1837. icon.addClass("fa-minus").removeClass("fa-spin fa-circle-o-notch");
  1838. else
  1839. icon.removeClass("fa-minus").addClass("fa-spin fa-circle-o-notch");
  1840. }
  1841. setDeletingState(true);
  1842. var warpID = elem.attr("data-warp-id");
  1843. if (!warpID)
  1844. return;
  1845. placeAjax.delete("/api/warps/" + warpID, null, "An unknown error occurred while attempting to delete the specified warp.", ()=>setDeletingState(false)).then((response)=>{
  1846. var index = this.warps.map((w)=>w.id).indexOf(warpID);
  1847. if (index >= 0)
  1848. this.warps.splice(index, 1);
  1849. this.layoutWarps();
  1850. }
  1851. ).catch(()=>{}
  1852. );
  1853. },
  1854. loadTemplates: function() {
  1855. var templateJSON = localStorage.getItem("templates");
  1856. if (!templateJSON)
  1857. return this.templates = [];
  1858. this.templates = JSON.parse(templateJSON);
  1859. },
  1860. saveTemplates: function() {
  1861. localStorage.setItem("templates", JSON.stringify(this.templates || []));
  1862. },
  1863. layoutTemplates: function() {
  1864. if (!this.templatesEnabled)
  1865. return $("#templates-ctn").text("Coming Soon");
  1866. if (!this.templates)
  1867. this.loadTemplates();
  1868. var templatesContainer = $("#templates-ctn");
  1869. var templateImgs = $("#template-images");
  1870. templatesContainer.html("");
  1871. templateImgs.html("");
  1872. var infoContainer = $("<div>").addClass("menu-section-content").appendTo($("<div>").addClass("menu-section-content-ctn").appendTo(templatesContainer));
  1873. $("<div>").addClass("warp-info template add").html("<span class=\"warp-title\"><i class=\"fa fa-plus\"></i></span>").click(this.addTemplateClicked.bind(this)).appendTo(infoContainer);
  1874. if (this.templates.length > 0) {
  1875. this.templates.forEach((template,index)=>{
  1876. var templateCtn = $("<div>").addClass("warp-info template").attr("data-template-id", index).attr("title", "Jump to the position of this template").appendTo(infoContainer);
  1877. templateCtn.click(this.moveToTemplateClicked.bind(this, templateCtn));
  1878. $("<div>").addClass("warp-delete").attr("title", "Delete this template").html("<i class=\"fa fa-minus fa-fw\"></i>").click(this.deleteTemplateClicked.bind(this, templateCtn)).appendTo(templateCtn);
  1879. $("<div>").addClass("warp-jump-to").attr("title", "Move this template to your current position").html("<i class=\"fa fa-map-pin fa-fw\"></i>").click(this.moveTemplateHereClicked.bind(this, templateCtn)).appendTo(templateCtn);
  1880. $("<div>").addClass("warp-visibility").attr("title", "Change the opacity of this template").html("<i class=\"fa fa-eye fa-fw\"></i>").click(this.changeOpacityOfTemplateClicked.bind(this, templateCtn)).appendTo(templateCtn);
  1881. $("<div>").addClass("warp-scale").attr("title", "Change the scale of this template").html("<i class=\"fa fa-expand fa-fw\"></i>").click(this.changeScaleOfTemplateClicked.bind(this, templateCtn)).appendTo(templateCtn);
  1882. $("<div>").addClass("template-img").css("background-image", `url(${template.url})`).appendTo(templateCtn);
  1883. var scale = (template.scale || 1) / 4;
  1884. $("<img>").attr("src", template.url).css({
  1885. top: template.pos.y,
  1886. left: template.pos.x,
  1887. transform: `scale(${scale}) translateZ(0) translate(-${50 / scale}%, -${50 / scale}%)`,
  1888. opacity: template.opacity
  1889. }).appendTo(templateImgs);
  1890. }
  1891. );
  1892. } else {
  1893. infoContainer.addClass("empty");
  1894. var explanation = $("<div>").addClass("warp-info template explanation").appendTo(infoContainer);
  1895. $("<span>").addClass("warp-title").text("Templates").appendTo(explanation);
  1896. $("<span>").addClass("warp-coordinates").text("Overlay an image on the canvas to use as a guide for your art.").appendTo(explanation);
  1897. }
  1898. },
  1899. addTemplateClicked: function() {
  1900. var app = this;
  1901. $("<input>").attr("type", "file").attr("accept", ".png,.jpg,.gif,.jpeg,.webm,.apng,.svg").hide().on("change", function() {
  1902. this.remove();
  1903. if (!this.files || !this.files[0])
  1904. return;
  1905. var reader = new FileReader();
  1906. reader.onload = (event)=>{
  1907. var dataURI = event.target.result;
  1908. app.templates.push({
  1909. pos: app.getCoordinates(),
  1910. url: dataURI,
  1911. opacity: 0.5,
  1912. scale: 1
  1913. });
  1914. app.layoutTemplates();
  1915. app.saveTemplates();
  1916. }
  1917. ;
  1918. reader.onerror = (event)=>{
  1919. console.error("Error trying to read template image.", event);
  1920. alert("An error occurred while attempting to read your template image.")
  1921. }
  1922. ;
  1923. reader.readAsDataURL(this.files[0]);
  1924. }).appendTo($("body")).click();
  1925. },
  1926. deleteTemplateClicked: function(elem, event) {
  1927. event.preventDefault();
  1928. event.stopPropagation();
  1929. if (!window.confirm("Are you sure you want to delete this template?"))
  1930. return;
  1931. var index = $(elem).attr("data-template-id");
  1932. if (!index || index < 0)
  1933. return;
  1934. this.templates.splice(index, 1);
  1935. this.layoutTemplates();
  1936. this.saveTemplates();
  1937. },
  1938. moveTemplateHereClicked: function(elem, event) {
  1939. event.preventDefault();
  1940. event.stopPropagation();
  1941. var index = $(elem).attr("data-template-id");
  1942. if (!index || index < 0)
  1943. return;
  1944. this.templates[index].pos = this.getCoordinates();
  1945. this.layoutTemplates();
  1946. this.saveTemplates();
  1947. },
  1948. changeOpacityOfTemplateClicked: function(elem, event) {
  1949. event.preventDefault();
  1950. event.stopPropagation();
  1951. var index = $(elem).attr("data-template-id");
  1952. if (!index || index < 0)
  1953. return;
  1954. var newOpacity = window.prompt("Enter the new desired opacity for this template (as a percentage):", (this.templates[index].opacity || 0.5) * 100);
  1955. if (!newOpacity)
  1956. return;
  1957. if (newOpacity > 100 || newOpacity < 0)
  1958. return window.alert("You must enter a value between 0 and 100.");
  1959. this.templates[index].opacity = newOpacity / 100;
  1960. this.layoutTemplates();
  1961. this.saveTemplates();
  1962. },
  1963. changeScaleOfTemplateClicked: function(elem, event) {
  1964. event.preventDefault();
  1965. event.stopPropagation();
  1966. var index = $(elem).attr("data-template-id");
  1967. if (!index || index < 0)
  1968. return;
  1969. var newScale = window.prompt("Enter the new desired scale for this template (relative to 1):", this.templates[index].scale || 1);
  1970. if (!newScale)
  1971. return;
  1972. this.templates[index].scale = newScale;
  1973. this.layoutTemplates();
  1974. this.saveTemplates();
  1975. },
  1976. moveToTemplateClicked: function(elem, event) {
  1977. event.preventDefault();
  1978. event.stopPropagation();
  1979. var index = $(elem).attr("data-template-id");
  1980. if (!index || index < 0)
  1981. return;
  1982. var pos = this.templates[index].pos;
  1983. this.zoomIntoPoint(pos.x, pos.y, false);
  1984. }
  1985. };
  1986. place.start($("canvas#place-canvas-draw")[0], $("#zoom-controller")[0], $("#camera-controller")[0], $("canvas#place-canvas")[0], $("#palette")[0], $("#coordinates")[0], $("#user-count")[0], $("#grid-hint")[0], $("#pixel-data-ctn")[0], $("#grid")[0]);
  1987. place.setZoomButton($("#zoom-button")[0]);
  1988. place.setGridButton($("#grid-button")[0]);
  1989. place.setCoordinatesButton($("#coordinates")[0]);
  1990. setInterval(place.protection, 15000);
  1991. $(".popout-control").click(function() {
  1992. place.popoutController.popoutVisibilityController.open();
  1993. place.popoutController.popoutVisibilityController.changeTab($(this).data("tab-name"));
  1994. })
  1995. $("#user-count").click(function() {
  1996. place.popoutController.popoutVisibilityController.open();
  1997. place.popoutController.popoutVisibilityController.changeTab("active-users");
  1998. });
  1999. var hash = hashHandler.getHash();
  2000. var hashKeys = Object.keys(hash);
  2001. if (hashKeys.indexOf("signin") > 0 || hashKeys.indexOf("logintext") > 0) {
  2002. if (hashKeys.indexOf("logintext") > 0) {
  2003. SignInDialogController.showErrorOnTab("sign-in", hash["logintext"])
  2004. hashHandler.deleteHashKey("logintext");
  2005. }
  2006. SignInDialogController.show("sign-in");
  2007. hashHandler.deleteHashKey("signin");
  2008. } else if (hashKeys.indexOf("signup") > 0) {
  2009. SignInDialogController.show("sign-up");
  2010. hashHandler.deleteHashKey("signup");
  2011. }
  2012. $("*[data-place-trigger]").click(function() {
  2013. var trigger = $(this).data("place-trigger");
  2014. if (trigger == "openSignInDialog") {
  2015. SignInDialogController.show("sign-in");
  2016. } else if (trigger == "openSignUpDialog") {
  2017. SignInDialogController.show("sign-up");
  2018. } else if (trigger == "openAuthDialog") {
  2019. SignInDialogController.show();
  2020. }
  2021. });
  2022. if (place.isSignedIn()) {
  2023. var changelogController = {
  2024. contentElement: $("#changelog-content"),
  2025. changelogs: null,
  2026. pagination: null,
  2027. isLoadingChangelogs: false,
  2028. setup: function() {
  2029. $(document).on("keydown", (e)=>{
  2030. var isLeft = e.keyCode == 37
  2031. , isRight = e.keyCode == 39;
  2032. if (ChangelogDialogController.isShowing() && (isLeft || isRight) && this.pagination) {
  2033. e.preventDefault();
  2034. if (this.pagination.next && isRight)
  2035. this.requestChangelogPage(this.pagination.next);
  2036. if (this.pagination.previous && isLeft)
  2037. this.requestChangelogPage(this.pagination.previous);
  2038. }
  2039. }
  2040. );
  2041. $("#nav-whats-new > a").click(()=>{
  2042. this.getChangelogsForShow("latest");
  2043. }
  2044. );
  2045. return this;
  2046. },
  2047. getChangelogsForShow: function(path="missed") {
  2048. if (this.isLoadingChangelogs)
  2049. return;
  2050. this.isLoadingChangelogs = true;
  2051. placeAjax.get("/api/changelog/" + path, null, null, ()=>{
  2052. this.isLoadingChangelogs = false;
  2053. }
  2054. ).then((data)=>{
  2055. placeAjax.post("/api/changelog/missed");
  2056. if (!data.changelogs && data.changelog)
  2057. data.changelogs = [data.changelog];
  2058. this.changelogs = data.changelogs
  2059. this.pagination = data.pagination;
  2060. this.layoutChangelogs();
  2061. if (this.changelogs && this.changelogs.length > 0)
  2062. this.showDialog();
  2063. }
  2064. ).catch((err)=>console.warn("Couldn't load changelogs: " + err));
  2065. },
  2066. requestChangelogPage: function(id) {
  2067. if (this.isLoadingChangelogs)
  2068. return;
  2069. this.isLoadingChangelogs = true;
  2070. placeAjax.get("/api/changelog/" + id, null, null, ()=>{
  2071. this.isLoadingChangelogs = false;
  2072. }
  2073. ).then((data)=>{
  2074. if (data.changelog)
  2075. this.changelogs = [data.changelog];
  2076. else
  2077. this.changelogs = [];
  2078. this.pagination = data.pagination;
  2079. this.layoutChangelogs();
  2080. }
  2081. ).catch((err)=>console.warn("Couldn't load changelog with ID:" + id + ", error: " + err));
  2082. },
  2083. showDialog: function() {
  2084. ChangelogDialogController.show();
  2085. },
  2086. layoutChangelogs: function() {
  2087. if (!this.changelogs)
  2088. return this.contentElement.addClass("needs-margin").text("Loading…");
  2089. if (this.changelogs.length <= 0)
  2090. return this.contentElement.addClass("needs-margin").text("There's no changelog to show.");
  2091. this.contentElement.html("").removeClass("needs-margin");
  2092. this.changelogs.forEach((changelog)=>{
  2093. var element = $("<div>").addClass("changelog-info").attr("data-changelog-version", changelog.version).appendTo(this.contentElement);
  2094. $("<p>").addClass("subhead extra-margin").text(this.getFormattedDate(changelog.date)).appendTo(element);
  2095. $("<p>").html(changelog.html).appendTo(element);
  2096. }
  2097. );
  2098. if (this.pagination) {
  2099. var paginationContainer = $("<ul>").addClass("pager").appendTo($("<nav>").attr("aria-label", "Changelog page navigation").appendTo(this.contentElement));
  2100. var previous = $("<a>").html("<span aria-hidden=\"true\">&larr;</span> Older").appendTo($("<li>").addClass("previous").appendTo(paginationContainer));
  2101. var next = $("<a>").html("Newer <span aria-hidden=\"true\">&rarr;</span>").appendTo($("<li>").addClass("next").appendTo(paginationContainer));
  2102. if (this.pagination.previous)
  2103. previous.attr("href", "javascript:void(0)").click(()=>this.requestChangelogPage(this.pagination.previous));
  2104. else
  2105. previous.parent().addClass("disabled");
  2106. if (this.pagination.next)
  2107. next.attr("href", "javascript:void(0)").click(()=>this.requestChangelogPage(this.pagination.next));
  2108. else
  2109. next.parent().addClass("disabled");
  2110. }
  2111. },
  2112. getFormattedDate: function(dateStr) {
  2113. var date = new Date(dateStr);
  2114. var t = new Date()
  2115. , y = new Date();
  2116. y.setDate(y.getDate() - 1);
  2117. if (date.toDateString() == (new Date()).toDateString())
  2118. return "Today";
  2119. else if (date.toDateString() == y.toDateString())
  2120. return "Yesterday";
  2121. else
  2122. return date.toLocaleDateString();
  2123. }
  2124. }.setup();
  2125. $(document).ready(function() {
  2126. changelogController.getChangelogsForShow();
  2127. });
  2128. }
  2129. $(document).ready(function() {
  2130. if (hashHandler.getHash()["beta"] != null) {
  2131. hashHandler.deleteHashKey("beta");
  2132. BetaDialogController.show();
  2133. }
  2134. });
  2135. $("#addLike").click(function() {
  2136. $.ajaxq('MyQueueLike', {
  2137. type: 'POST',
  2138. url: 'api.php?te=1',
  2139. data: {
  2140. user_id: user.user_id,
  2141. token: user.token,
  2142. setLike: 1,
  2143. x: lastClickedInfo.x,
  2144. y: lastClickedInfo.y
  2145. },
  2146. success: function(returnedData) {
  2147. if (returnedData == "ok") {
  2148. showNotify("Вы поставили лайк!", 3000);
  2149. } else {
  2150. if (returnedData == "time") {
  2151. showNotify("Лайк можно ставить раз в 10 минут!", 3000);
  2152. }
  2153. if (returnedData == "double") {
  2154. showNotify("Вы уже ставили лайк этому автору!", 3000);
  2155. }
  2156. if (returnedData == "self") {
  2157. showNotify("Нельзя ставить лайк самому себе!", 3000);
  2158. }
  2159. if (returnedData == "null") {
  2160. showNotify("Некому ставить лайк!", 3000);
  2161. }
  2162. }
  2163. }
  2164. });
  2165. });
  2166. $("#nav-help > a").click(()=>HelpDialogController.show());
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement