Problem
Editor-1
Built with
NextJs
ReactJs
Chakra-UI
Open Source editor
Editor-2
Built With
NextJs
ReactJs
Open Source editor
No chakra UI
Editor-2 has no problem but Editor-1 has a problem.
To reproduce
Paste the below markdown into both editors one by one
# Save your application from crashing by the wrong use of Web Storage API or localStorage in the browser
While coding front-end applications, we may need to store some data on the client side. There are four types of storage on the browser namely cookie, localStorage, sessionStorage and indexDB.
## Github source
see code for
- [getLocalStorage](https://gist.github.com/ats1999/877f00d4618f091e606bd77fd0a58f8c#file-save-web-storage-js-L2)
- [setLocalStorage](https://gist.github.com/ats1999/877f00d4618f091e606bd77fd0a58f8c#file-save-web-storage-js-L12)
- [isCookie](https://gist.github.com/ats1999/877f00d4618f091e606bd77fd0a58f8c#file-save-web-storage-js-L23)
## What is `Web Storage API`
The Web Storage API provides mechanisms by which browsers can store key/value pairs, in a much more intuitive fashion than using cookies.
<https://developer.mozilla.org/en-US/docs/Web/API/Web_Storage_API>
***
When you refer to the above-mentioned document, then you'll get the importance of **web storage**. But do you know that if you are not using it safely, then it'll break your application from further processing? Meaning, if the cookie is blocked, then you won't be able to access `web storage API`, it'll throw an error like below.
// error - when cookie is blocked
Uncaught DOMException: Failed to read the 'localStorage' property from 'Window': Access is denied for this document.
at file:///home/rahul/Desktop/projects/test/index.js:1:1
## Let's try
[block-cookie](https://www.google.com/search?q=how+to+block+cookie&oq=how+to+block+cookie&aqs=chrome..69i57.4096j0j1&sourceid=chrome&ie=UTF-8)
> You can refer to the above link to know more about, how can you block cookies.
**HTML file**
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<script src="index.js"></script>
<title>Document</title>
</head>
<body>
<h1>Hello</h1>
</body>
</html>
**JavaScript file**
// index.js
if(localStorage)
console.log("local item storage is persent")
console.log("hello")
Now, after blocking the cookie, load the HTML file in a browser. You won't see any information on browser console`(hello), etc`. This is because, once your script encountered an exception, the javascript engine stops further processing.
In order to avoid crashing the application, we need to wrap the code into `try` and `catch`.
// index.js
try {
if(localStorage)
console.log("local item storage is persent")
} catch (error) {
console.log(error)
}
console.log("hello")
Now, you can try the above code. In the above code, exception is handled by the `catch` block. Although, we still can not access `localStorage` this way our application will not crash.
## Do I need to `try/catch` everywhere?
Writing `try/catch` everywhere can be a tedious task. To avoid writing `try/catch`, we can wrap it into another function.
/**
* get item from localstorage
* #param {String} str name of attribte in local storage`
* #returns item | false
*/
function getLocalStorage(str){
try {
return localStorage.getItem(str);
} catch (error) {
return false;
}
}
// call
getLocalStorage('item');
## conclusion
instead of using `localStorage.getItem(str)` , we should use `getLocalStorage(str)`.
If you liked, then please give a star -> <https://gist.github.com/ats1999/877f00d4618f091e606bd77fd0a58f8c>
## Thanku
Now
Compare the scroll bar of both editors.
Editor-1 scroll bar
Editor-2 scroll bar
The Problem
You can see that the editor-1 scroll bar is ending before the end of the editor. But, the editor-2 scroll bar is ending at the right position.
The only difference in both is that editor-1 uses chakra-ui as the UI framework in the entire application.
I was able to create the desired result by adding a height: 100% to the div element (see image).
Here was the update that was made. If you need to use global css, then I'd suggest targeting .ProseMirror to add the height property. I simply added inline css using the DOM in Chrome to show what change I made:
Image before adding in the height property. Notice the gap. Not just with the scrollbar but with the text itself. It doesn't go all the way to the bottom.
Image after the update, now it looks like Editor 2!
Related
I have been on an adventure to get a sportsbook dashboard in my mancave. With the main goal to display the lines of my Prefered sportsbook. Based on some googling and digging all the API's cost money. I settled on using the Game Center by Pregame, which I use quite often anyways.
So they have embed code for the GameCenter and I have a fairly basic HTML page going but somethings not quite right and it's displaying all wonky. I can't tell if it's my code or Pregame that is the issue. Any help or guidance would be appreciated.
Link to the Static Page: https://dashboard.megustasports.com/Untitled-1.html
Pregame Gamecenter: https://pregame.com/game-center
EDIT
Here are the errors from the Chrome console
Indicate whether to send a cookie in a cross-site request by
specifying its SameSite attribute Because a cookie's SameSite
attribute was not set or is invalid, it defaults to SameSite=Lax,
which prevents the cookie from being sent in a cross-site request.
This behavior protects user data from accidentally leaking to third
parties and cross-site request forgery.
Resolve this issue by updating the attributes of the cookie: Specify
SameSite=None and Secure if the cookie should be sent in cross-site
requests. This enables third-party use. Specify SameSite=Strict or
SameSite=Lax if the cookie should not be sent in cross-site requests
9 cookies Name Domain & Path .te.dpr pregame.com/
_ga .pregame.com/
_gid .pregame.com/ .te.w pregame.com/ Telligent.Evolution-UI pregame.com/ tzoffset pregame.com/
tzid pregame.com/ .te.dpr pregame.com/utility
.te.w pregame.com/utility 2 requests pg.authentication.js
error-notfound.aspx?item=%2fassets%2fscripts%2fpg.…entication&user=extranet%5cAnonymous&site=website
Here is the HTML I am currently using:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Here the title</title>
<style>
*{
margin: 0px;
}
iframe {
display: block !important;
width: 100%;
height: 100vh;
}
</style>
</head>
<body>
<script src="https://pregame.com/assets/scripts/tear/tear.js" data-type="generic" data-url="https://pregame.com/game-center?ts_i=game-center"></script>
</body>
</html>
In theory, the end result should only contain the table from the page linked above and look something similar to this:
Instead of using an iframe, try making a HTTP request and storing that in a div:
var cors_api_url = 'https://cors-anywhere.herokuapp.com/';
function doCORSRequest(options, printResult) {
var x = new XMLHttpRequest();
x.open(options.method, cors_api_url + options.url);
x.onload = x.onerror = function() {
printResult(
(x.responseText || '')
);
};
if (/^POST/i.test(options.method)) {
x.setRequestHeader('Content-Type', 'application/x-www-form-urlencoded');
}
x.send(options.data);
}
doCORSRequest({
method: 'GET',
url: 'https://pregame.com/game-center/',
data: ''
}, function printResult(result) {
document.querySelector('.result').innerHTML = result;
});
<div class="result"></div>
Problem
CORS is designed to prevent malicious websites from imitating a legitimate one. The Pregame Game Center’s CORS policy requires that the website embedding an iframe containing their website be on the same domain. To use an iframe from your domain, the Pregame Game Center developers would have to add your domain to their CORS policy.
Solution
Consider instead programmatically navigating their website and pulling information you need from it (scraping), then creating your own website to display that information. This is the most roundabout way, but generally accepted if there is no API you can use to access the information you need. Through investigation you may even come across a JSON formatted endpoint used by their front end to retrieve information to be displayed (their private API) that you can use.
Note
Scraping and republishing information produced by Pregame Game Center may be against their terms and conditions. You may be able to avoid legal implications if you host the website locally, or remotely behind authentication.
References
CORS: https://developer.mozilla.org/en-US/docs/Web/HTTP/CORS
Web scraping (Python - Beautiful Soup) Tutorial: https://realpython.com/beautiful-soup-web-scraper-python
Django (Python web framework): https://www.djangoproject.com
You cannot use iframe to display some of the websites like Google.
This is a security measure implemented to protect their website and customer data from being attacked.
If you want to get some details of the website, you can use their API if they provide.
That is the best option.
You can search for a bunch of API's available on the web for your requirement.
How can one send <head> contents before the controller finishes? The idea is to start loading CSS as soon as possible (don't wait for controller action).
Sample scenario:
// in the controller
sleep(5);
This gives:
blank page for 5 seconds -> display the head -> start loading CSS -> body
The flow I want to get is:
Send head -> start loading CSS -> wait for the controller -> send rest of the page (body)
The <head> is now in layout.phtml, which later includes the index controller script (index.phtml).
Maybe I could have <head> as a partial and send it somehow before the whole layout?
One approach is to create an abstract controller that all controllers extend, and in the onDispatch function render the head template and flush:
public function onDispatch(MvcEvent $e) {
$renderer = $this->getServiceLocator()->get('ViewRenderer');
$content = new ViewModel();
$content->setTemplate('path/to/head.phtml');
$content = $renderer->render($content);
echo $content;
flush();
parent::onDispatch($e);
}
Drawbacks to this approach:
You have no access to the headTitle, headMeta, headLink, headScript and other view helpers elsewhere in your application (it is possible in a controller or viewscript to add a style sheet and js plugin for just that page).
You will be unable to perform redirects as a response has already been sent
You can't gzip the content as well as flushing it
Some versions of Microsoft Internet Explorer will only start to display the page after they have received 256 bytes of output, so you may need to send extra whitespace before flushing to get those browsers to display the page.
In theory, you could use this approach to load all static content in the layout before echoing $this->content - such as logo, navigation, search bar, etc etc.
As I've stated, this breaks redirects meaning helpers and plugins such a PostRedirectGet will not work.
I am trying to optimise the loading of Polymer Elements in my Polymer based web app. In particular I am concentrating my effort around the initial start up screens. Users will have to log on if they don't have a valid jwt token held in a cookie.
index.html loads an application element <pas-app> which in turn loads an session manager (<pas-eession>). Since the normal startup will be when the user is already logged on the element that handles input of user name and password (<pas-logon>) is hidden behind a <template is="dom-if"> element inside of <pas-session>and I have added the async flag to its html import line in that element as well - thus :
<link rel="import" href="pas-logon.html" async>
However, in chrome (I don't experience this in firefox, where html imports are polyfilled) this async seems to flow over embedded <script> element inside the custom element. In particular I get a type error because the script to cause it to be regestered as a custom element thinks Polymer is not a function.
I suspect I am using the wrong kind of async flag - is there a way to specify that the html import should not block the current element, but should block the scripts inside itself when loaded.
I think I had the same problem today and found this question when searching for a solution. When using importHref async I get errors like [paper-radio-button::_flattenBehaviorsList]: behavior is null, check for missing or 404 import and dependencies are not loaded in the right order. When I change to async = false the error messages are gone.
It seems that this is a known bug of Polymer or probably Chrome https://github.com/Polymer/polymer/issues/2522
I need to remotely control a solenoid with an Arduino, from about 2000 feet away. So far, it works: I designed a control circuit that fires based upon a logic-level signal from pin 9.
My problem: the initial Arduino code sent up a web page over ethernet each time the form was submitted, but if the user tried to toggle the state too quickly, the transmission was interrupted and the whole system puked. It was also slow to load.
My attempted solution: I created an HTML document on a local page to do what I need done, and indeed it does: I can control the Solenoid. However once the links which control the commands are submitted, there's no redirect back to the local control page, and after much Google-fu I can't seem to implement it in this way. Is this possible? Is this a good approach?
<HTML>
<HEAD>
<TITLE>Sensor-Cleaning Control</TITLE>
</HEAD>
<BODY>
<H1>Solenoid Remote Actuation</H1>
<hr />
<br />
Turn On Solenoid
Turn Off Solenoid<br />
<button type="button" onclick="location.href='http://192.168.0.88/?sol_on'">On</button>
<button type="button" onclick="location.href='http://192.168.0.88/?sol_off'">Off</button>
<button type="button" onclick="location.href='http://192.168.0.88/?toggle'">Toggle</button>
<br />
<p>(Check pin 9 LED ''L9'' to make sure this code is working)</p>
</BODY>
</HTML>
So if the Arduino sees "sol_on" it turns the solenoid on; "sol_off" off, and you can guess what "toggle" does. I'm pretty comfortable coding, but I know nothing of javascript, CSS, or PHP. I'm not afraid of implementing those, it just needs to be clear for me to do so. Note that there's some redundancy in the code above, I left it so that I could test multiple approaches to the UI.
If I'm understanding you correctly, your best approach would probably be to use Ajax, where your web page uses an asynchronous Javascript call to do the toggling/on/off.
Effectively, you have the web page as shown, but instead of links to the Arduino "pages", clicking each link fires off an asynchronous request to the Arudino page, leaving your current page in the browser while still prodding the URL on the Arduino web server.
If you're not that familiar with Javascript, possibly a sensible approach would be to use jQuery, a Javascript library which insulates you somewhat from differences between browsers, and encapsulates things like Ajax requests quite nicely.
Here are some simple steps:
1) Download the latest production jQuery. I'm using 2.0.3 from here for this example.
2) Put it in the same directory as your web page, so we can include it easily.
3) Convert your web page to use Ajax with jQuery. (I've also converted it to something a little closer to the current web standard, HTML5):
<!DOCTYPE html>
<html>
<head>
<title>Sensor-Cleaning Control</title>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />
<!-- Include jQuery so we can use its simple goodness -->
<script src="jquery-2.0.3.min.js"></script>
<script>
/* This function will be called by the onclick handlers of the buttons */
function solenoid(url) {
// Use jQuery's Ajax functionality to prod the given URL without
// reloading this page or visiting another one:
$.ajax(url);
}
</script>
</head>
<body>
<h1>Solenoid Remote Actuation</h1>
<button type="button" onclick="solenoid('http://192.168.0.88/?sol_on');">On</button>
<button type="button" onclick="solenoid('http://192.168.0.88/?sol_off');">Off</button>
<button type="button" onclick="solenoid('http://192.168.0.88/?toggle');">Toggle</button>
<p>(Check pin 9 LED ''L9'' to make sure this code is working)</p>
</body>
</html>
The main things to note are:
1) The inclusion of the jQuery library, so we can use its ajax() call and fire off http requests in the background with ease no matter which browser we're on.
2) I've replaced your existing onclick events with a call to a new function called solenoid, that takes a URL as a parameter.
3) The solenoid function, defined in the <script> at the top, takes the URL that was passed in and uses jQuery's ajax() call to poke the given URL. This happens in the "background", i.e. without any page (re)load.
From here, you could expand this in all sorts of ways. This code could, for example, read a short response from the Arduino and handle it in the background, too, perhaps indicating the current state of the solenoid.
(Given the simplicity of what I'm doing here, I'm sure this could be done in a more "lightweight" way in pure Javascript without jQuery, but that would have involved a chunk more slightly scary code in this example to ensure the Ajax stuff worked in many different browsers -- there's some browser inconsistency in how the underlying object (an XMLHttpRequest) used by Ajax is created. I figured for a Javascript beginner, simpler was probably better...)
Well, i don't know your Arduino's based http server, but it certainly shall reply all requests, either with an 200 http status, that means "OK" or with any other error message like 400, that means "Bad Request". While your web application is waiting for a response, you can block (or hide) the page (or some elements) so the user will be unable to start a click-frenzy and mess up everything while he should be waiting the server's (Arduino) response.
You can use an ajax call using JQuery, so you will be able to "do something" after calling the url with your "Arduino code", either in case of success or fail.
Please see the example below:
<html>
<head>
<script src="../scripts/jquery-2.0.3.min.js"></script>
<script>
function callArduinoCode(var code) {
jQuery.ajax({
type: "GET",
url: "http://192.168.0.88/?" + code,
data: dados,
beforeSend: function() {
// Hide links, show loading message...
$("#controls").css("display","none");
$("#loading").css("display","block");
},
success: function( data ){
// Hide loading message, show links again...
$("#controls").css("display","block");
$("#loading").css("display","none");
},
error: function (xhr, ajaxOptions, thrownError){
alert("Failed, HTTP Status was " + xhr.status);
// Hide loading message, show links again...
$("#controls").css("display","block");
$("#loading").css("display","none");
}
});
return false;
}
</script>
</head>
<body>
<div id="controls">
<!-- your links here -->
<a onClick="callArduinoCode('sol_on'); return false;">Turn Solenoid ON</a>
<a onClick="callArduinoCode('sol_off'); return false;">Turn Solenoid OFF</a>
</div>
<div id="loading" style="display:none;">
Loading, please wait...
</div>
</body>
</html>
You can get JQuery at jquery.com
Good Luck!
No need to add any library / framework to accomplish what you need. Even you can achieve it without javascript at all. Simply add an invisible IFRAME in your HTML file with name attribute set. In following example we'll use "Arduino" as the IFRAME's name, but you can use any valid element name you'd like.
<IFRAME name="Arduino" style="display:none"></IFRAME>
Next, add target attribute on your link element (the 'A' tags) with value specified as the IFRAME's name, i.e.:
Turn On Solenoid
When you click on the link, request sent to your Arduino and resulting response will be directed to the the invisible IFRAME without navigating away from currently viewed page.
For the button element, prefix location.href in onclick handler with the IFRAME's name:
<BUTTON onclick="Arduino.location.href='//192.168.0.88?sol_on';">On</BUTTON>
I'm currently trying to build a new website, nothing special, nice and small, but I'm stuck at the very beginning.
My problems are clean URLs and page navigation. I want to do it "the right way".
What I would like to have:
I use CodeIgniter to get clean URLs like
"www.example.com/hello/world"
jQuery helps me using ajax, so I can
.load() additional content
Now I want to use HTML5 features like pushstate to
get rid of the # in the URL
It should be possible to go back and forth without a page refresh but the page will still display the right content according to the current URL.
It should also be possible to reload a page without getting a 404 error. The site should exist thanks to CodeIgniter. (there is a controller and a view)
For example:
A very basic website. Two links, called "foo" and "bar" and a emtpy div box beneath them.
The basic URL is example.com
When you click on "foo" the URL changes to "example.com/foo" without reloading and the div box gets new content with jQuery .load(). The same goes for the other link, just of course different content and URL.
After clicking "foo" and then "bar" the back button will bring me back to "example.com/foo" with the according content. If I load this link directly or refresh the page, it will look the same. No 404 error or something.
Just think about this page and tell me how you would do this.
I would really love to have this kind of navigation and so I tried several things.
So far...
I know how to use CodeIgniter to get the URLs like this. I know how to use jQuery to load additional content and while I don't fully understand the html5 pushstate stuff, I at least got it to work somehow.
But I can't get it to work all together.
My code right now is a mess, that's the reason I don't really want to post it here. I looked at different tutorials and copy pasted some code together. Would be better to upload my CI folder I guess.
Some of the tutorials I looked at:
Dive into HTML5
HTML5 demos
Mozilla manipulating the browser history
Saner HTML5 history
Github: History.js
(max. number of links reached :/)
I think my main problem is, that everybody tries to make it compatible with all browsers and different versions, adds scripts/jQuery plugins and whatnot and I get confused by all the additional code. There is more code between my script-tags then actual html content.
Could somebody post the most basic method how to use HTML5 for my example page?
My failed attemp:
On my test page, when I go back, the URL changes, but the div box will still show the same content, not the old one. I also don't know how to change the URL in the script according to the href attribute from the link. Is there something like $(this).attr('href'), that changes according to which link I click? Right now I would have to use a script for every link, which of course is bad.
When I refresh the site, CodeIgniter kicks in and loads the view, but really only the view by itself, the one I loaded with ajax, not the whole page. But I guess that should be easy to fix with a layout and the right controller settings. Haven't paid much attention to this yet.
Thanks in advance for any help.
If you have suggestions, ideas, or simple just want to mention something, please let me know.
regards
DiLer
I've put up a successful minimal example of HTML5 history here: http://cairo140.github.com/html5-history-example/one.html
The easiest way to get into HTML5 pushstate in my opinion is to ignore the framework for a while and use the most simplistic state transition possible: a wholesale replacement of the <body> and <title> elements. Outside of those elements, the rest of the markup is probably just boilerplate, although if it varies (e.g., if you change the class on HTML in the backend), you can adapt that.
What a dynamic backend like CI does is essentially fake the existence of data at particular locations (identified by the URL) by generating it dynamically on the fly. We can abstract away from the effect of the framework by literally creating the resources and putting them in locations through which your web server (Apache, probably) will simply identify them and feed them on through. We'll have a very simple file system structure relative to the domain root:
/one.html
/two.html
/assets/application.js
Those are the only three files we're working with.
Here's the code for the two HTML files. If you're at the level when you're dealing with HTML5 features, you should be able to understand the markup, but if I didn't make something clear, just leave a comment, and I'll walk you through it:
one.html
<!doctype html>
<html>
<head>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.6.2/jquery.js"></script>
<script src="assets/application.js"></script>
<title>One</title>
</head>
<body>
<div class="container">
<h1>One</h1>
Two
</div>
</body>
</html>
two.html
<!doctype html>
<html>
<head>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.6.2/jquery.js"></script>
<script src="assets/application.js"></script>
<title>Two</title>
</head>
<body>
<div class="container">
<h1>Two</h1>
One
</div>
</body>
</html>
You'll notice that if you load one.html through your browser, you can click on the link to two.html, which will load and display a new page. And from two.html, you can do the same back to one.html. Cool.
Now, for the history part:
assets/application.js
$(function(){
var replacePage = function(url) {
$.ajax({
url: url,
type: 'get',
dataType: 'html',
success: function(data){
var dom = $(data);
var title = dom.filter('title').text();
var html = dom.filter('.container').html();
$('title').text(title);
$('.container').html(html);
}
});
}
$('a').live('click', function(e){
history.pushState(null, null, this.href);
replacePage(this.href);
e.preventDefault();
});
$(window).bind('popstate', function(){
replacePage(location.pathname);
});
});
How it works
I define replacePage within the jQuery ready callback to do some straightforward loading of the URL in the argument and to replace the contents of the title and .container elements with those retrieved remotely.
The live call means that any link clicked on the page will trigger the callback, and the callback pushes the state to the href in the link and calls replacePage. It also uses e.preventDefault to prevent the link from being processed the normal way.
Finally, there's a popstate event that fires when a user uses browser-based page navigation (back, forward). We bind a simple callback to that event. Of note is that I couldn't get the version on the Dive Into HTML page to work for some reason in FF for Mac. No clue why.
How to extend it
This extremely basic example can more or less be transplanted onto any site because it does a very uncreative transition: HTML replacement. I suggest you can use this as a foundation and transition into more creative transitions. One example of what you could do would be to emulate what Github does with the directory navigation in its repositories. It's an intermediate manoever that requires floats and overflow management. You could start with a simpler transition like appending the .container in the loaded page to the DOM and then animating the old container to {height: 0}.
Addressing your specific "For example"
You're on the right track for using HTML5 history, but you need to clarify your idea of exactly what /foo and /bar will contain. Basically, you're going to have three pages: /, /foo, and /bar. / will have an empty container div. /foo will be identical to / except in that container div has some foo content in it. /bar will be identical to /foo except in that the container div has some bar content in it. Now, the question comes to how you would extract the contents of the container through Javascript. Assuming that your /foo body tag looked something like this:
<body>
foo
bar
<div class="container">foo</div>
</body>
Then you would extract it from the response data through var html = $(data).filter('.container').html() and then put it back into the parent page through $('.container').html(html). You use filter instead of the much more reasonable find because from some wacky reason, jQuery's DOM parser produces a jQuery object containing every child of the head and every child of the body elements instead of just a jQuery object wrapping the html element. I don't know why.
The rest is just adapting this back into the "vanilla" version above. If you are stuck at any particular stage, let me know, and I can guide you better though it.
Code
https://github.com/cairo140/html5-history-example
Try this in your controller:
if (!$this->input->is_ajax_request())
$this->load->view('header');
$this->load->view('your_view', $data);
if (!$this->input->is_ajax_request())
$this->load->view('footer');