WinHTTP getElementsByTagName() only shows opening tag for "section" - vba

Using AhtuHotkey 2.0 Beta1 (i assume VBA script as well) getElementsByTagName() only shows opening tag for HTML5 tags section and nav however works with all other HTML4 tags.
AutoHotkey Code
HTMLObj := ComObject("HTMLfile")
HTMLObj.write(HTML)
DOMObj := HTMLFileObj.getElementsByTagName("section")
msgbox DOMObj[0].outerHTML
following will return just opening tag <section class=mysection> i think it simply does not know how to handle HTML5 tags. Is there solution, i am on Windows 7 x64 Service Pack 1

Old versions of IE('s HTML parser) treat unknown elements as inline elements by default. That means the parser auto-closes them as soon the next known block element is encountered.
Try this (a bare-bones version of the much more comprehensive https://github.com/aFarkas/html5shiv):
html5shim =
(
<script>
document.createElement('header');
document.createElement('section');
document.createElement('main');
document.createElement('article');
document.createElement('aside');
document.createElement('nav');
document.createElement('footer');
</script>
)
HTMLObj := ComObject("HTMLfile")
HTMLObj.write(html5shim)
HTMLObj.write(HTML)
DOMObj := HTMLFileObj.getElementsByTagName("section")
msgbox DOMObj[0].outerHTML
An alternative way would be to add CSS that declares these elements as block elements:
<style type="text/css">
header, section, main, article, aside, nav, footer { display: block; }
</script>

Related

Apply vue-katex to content loaded from static folder

I'm trying to make a blog using Vue as laid out in the excellent demo here. I'd like to include some mathematical formulas and equations in my blog, so I thought I'd try to use vue-katex. vue-katex formats my mathematical notation perfectly when I put all my KaTeX HTML directly into my Vue templates, but to create a useable blog I need to keep my content separate from my templates (as shown in the demo).
I can't get vue-katex to format HTML content in the static folder. That's what I'd like help with.
Setup
I cloned the github repo for the demo.
I added vue-katex to package.json:
"vue-katex": "^0.1.2",
I added the KaTeX CSS to index.html:
<!-- KaTeX styles -->
<link
rel="stylesheet"
href="https://cdnjs.cloudflare.com/ajax/libs/KaTeX/0.9.0-alpha2/katex.min.css"
integrity="sha384-exe4Ak6B0EoJI0ogGxjJ8rn+RN3ftPnEQrGwX59KTCl5ybGzvHGKjhPKk/KC3abb"
crossorigin="anonymous"
>
I added the import statement to src/App.vue:
import Vue from 'vue'
import VueKatex from 'vue-katex'
Vue.use(VueKatex)
and I added a simple line of HTML with KaTeX to the BlogPost template:
<p>Here's an equation in the actual Vue template: <div class="equation" v-katex="'X \\sim N(\\mu, \\sigma^2)'"></div></p>
As I said, this works - I see formatted mathematical notation in my blog post (URL http://localhost:8080/read/neque-libero-convallis-eget):
However, I need different equations for every blog post, of course.
So I tried adding KaTeX HTML to the "content" field in the JSON for the first blog post: static/api/post/neque-libero-convallis-eget.json. I changed the "content" line to:
"content": "Here's an equation in the static folder: <div class=\"equation\" v-katex=\"'X \\sim N(\\mu, \\sigma^2)'\"></div>",
This content appears on the page, but the equation doesn't render. I see this: (the text appears but no equation is shown)
When I use Developer Tools to inspect the HTML on the page, I see this:
You can see that vue-katex has been applied to the equation I put in the template directly: it has parsed the HTML I typed into lots of spans with all the mathematical symbols, which are showing perfectly.
However the KaTeX HTML I've added to the "content" in the static folder has simply been placed on the page exactly as I typed it, and is therefore not showing up as an equation on the page. I really need to keep my blog post content in this static folder - I don't want to have to create a different .vue file for each blog post, that defeats the point!
My question is: is there a way to manually "apply" vue-katex to the HTML I place in the static folder, when it loads? Perhaps there is something I can add to the plugins/resource/index.js file, since this contains the function that loads the data from the static folder?
Many thanks in advance for any help.
*Disclaimer: I'm definitely no expert / authority on what I'm about to explain!
One thing to remember is that Vue reads the templates you write, and then replaces them as reactive components. This means that although you often write Vue attributes like v-for, v-html or in this case v-katex these attributes are only useful up until the app or component is mounted.
With this in mind, if you have a Vue app that ajax loads some html, its not going to be able to rerender itself with those Vue bindings in place.
I have somewhat ignored your current set up and set about solving the issue in another way.
Step 1: Reformat your data from the server side
I've put the posts into an array, and each post contains the template (just a string of html) and the equations separately as an array. I've used [e1] in the post as a placeholder for where the katex will go.
var postsFromServer = [{
content : `<div>
<h2>Crazy equation</h2>
<p>Look here!</p>
[e1]
</div>`,
equations : [
{
key : 'e1',
value : "c = \\pm\\sqrt{a^2 + b^2}"
}
]
}];
Step 2: When the post is rendered, do some work on it
Rather than just use v-html="post.content", I've wrapped the html output in a method
<div id="app">
<div v-for="post in posts" v-html="parsePostContent(post)">
</div>
</div>
Step 3: Create a method that renders all the katex, and then replaces the placeholders in the post
methods : {
parsePostContent(post){
// Loop through every equation that we have in our post from the server
for(var e = 0; e < post.equations.length; e++){
// Get the raw katex text
var equation = post.equations[e].value;
// Get the placeholder i.e. e1
var position = post.equations[e].key;
// Replace [e1] in the post content with the rendered katex
post.content = post.content.replace("[" + position + "]", katex.renderToString(equation));
}
// Return
return post.content;
}
}
Here is the whole set up, which renders Katex:
https://codepen.io/EightArmsHQ/pen/qxzEQP?editors=1010

Get a css property with selenium webdriver by selectors

I am doing a exercise with client java to use cssSelector method to retrieve some objects having a particular web element's CSS property.
The statement
driver.findElements(By.cssSelector(".item-result .content-main .block-opening"))
returns all elements from page using the class ".item-result .content-main .block-opening" (refer to my blocks below) and all is fine up to there!
Nevertheless, I only want those which have a property text-indent whose value is -999em. To perform it, I first use
driver.findElements(By.cssSelector(".item-result .content-main .block-opening[text-indent]"))
to retrieve all elements having a text-indent css property but I realize that no element is matching while I have text-indent property inside my css block.
HTML block
<html id="ng-app" data-ng-app="rwd" data-ng-controller="AppCtrl" lang="fr" class="ng-
scope">
<head>...</head>
<body>
...
<span class="block-opening icon-time-filled ng-scope" data-ng-if="bloc.openClosed ==
'O'">Ouvert</span>
...
</body>
</html>
CSS block
.item-result .content-main .block-opening {
width: 25px;
color: #a1a1a1;
text-indent: -999em;
}
I was hoping to find exactly what i want to by the use of
driver.findElements(By.cssSelector(".item-result .content-main .block-opening[text-indent='-999em']"))
Since elements related to text-indent are not found, I am blocked to find those having text-indent to -999em.
Please any help would be appreciated!
Perhaps a little bit of a longer route but you could try getting a list of all the elements and checking the css-properties, with the appropriate method.
List<Webelement> elements = driver.findElements(By.cssSelector(".item-result .content-main .block-opening"));
for (Webelement element : elements) {
if (element.getCssValue("text-indent").equals("-999em")) {
return element;
}
}
Caveat, I've never tried to get the text-indent value, as such I can't guarantee that the above will work.
http://selenium.googlecode.com/git/docs/api/java/org/openqa/selenium/WebElement.html#getCssValue(java.lang.String)
You can locate that element using xpath using inner text value
By.xpath("//span[text()='Ouvert']")

How to add id using dojo.query to search element

I'm trying to add id to a element using dojo.query. I'm not sure if it's possible though. I trying to use the code below to add the id but it's not working.
dojo.query('div[style=""]').attr("id","main-body");
<div style="">
content
</div>
If this is not possible, is there another way to do it? Using javascript or jquery? Thanks.
Your way of adding an id to an element is correct.
The code runs fine for me in Firefox 17 and Chrome 23 but I have an issue in IE9. I suspect you may have the same issue.
In IE9 the query div[style=""] returns no results. The funny thing is,it works fine in compatibility mode!
t seems that in IE9 in normal mode if an HTML element has an inline empty style attribute, that attribute is not being preserved when the element is added to the DOM.
So a solution would be to use a different query to find the divs you want.
You could try to find the divs with an empty style attributes OR with no style attribute at all.
A query like this should work:
div[style=""], div:not([style])
Take a look at the following example:
<!DOCTYPE html>
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<title>Test Page</title>
<script type="text/javascript" src="//ajax.googleapis.com/ajax/libs/dojo/1.8.2/dojo/dojo.js"></script>
<script type="text/javascript">
dojo.require("dojo.NodeList-manipulate");//just for the innerHTML() function
dojo.addOnLoad(function () {
var nodeListByAttr = dojo.query('div[style=""], div:not([style])');
alert('Search by attribute nodeList length:' + nodeListByAttr.length);
nodeListByAttr.attr("id", "main-body");
var nodeListByID = dojo.query('#main-body');
alert('Search by id nodeList length:' + nodeListByID.length);
nodeListByID.innerHTML('Content set after finding the element by ID');
});
</script>
</head>
<body>
<div style="">
</div>
</body>
</html>
Hope this helps
#Nikanos' answer covers the query issue, I would like to add, that any query returns an array of elements, in case of Dojo it is dojo/NodeList.
The problem is you are about to assign the same id to multiple DOM nodes, especially with query containing div:not([style]). I recommend to use more specific query like first div child of body:
var nodes = dojo.query('body > div:first-child');
nodes.attr("id", "main-body");
To make it more robust, do not manipulate all the nodes, just the first node (even through there should be just one):
dojo.query('body > div:first-child')[0].id = "main-body";
This work also in IE9, see it in action: http://jsfiddle.net/phusick/JN4cz/
The same example written in Modern Dojo: http://jsfiddle.net/phusick/BReda/

Access Elements of a DOJO DIV

I have two Hyper Links on to a DOJO DIv
var create = dojo.create("div",{
id:"create_links",
className:"iconRow1",
innerHTML:"<a class='popupLink' href='javascript:openCreateDialog()'>Create </a> <span>|</span><a href='javascript:openUploadDialog()'>Batch </a>"
},dojo.query(".ui-jqgrid-titlebar")[0]);
On click of the Batch Hyperlink , i have a function
function openUploadDialog()
{
// Here i want to disable the Create Hyper Link tried this way
dojo.byId('create_links')[1].disabled=true; // Not working
}
See whether i can answer your question.
HTML Part:
<div id="create_links">
g
h
</div>
JS Part:
dojo.addOnLoad(function() {
var a = dojo.query("#create_links a")[1];
dojo.connect(a,'click',function(e){
console.log(e.preventDefault())
})
})
#Kiran, you are treating the return of dojo.byId('create_links') like an array when that statement will return to you a node on the dom.
Also, hyperlinks don't support a disabled attribute to prevent them from being actionable. You could probably create a click handler that returns false to accomplish this type of functionality, or like #rajkamal mentioned, calling e.preventDefault(). #rajkamal also provides a good solution to selection the link properly.

How to prevent CKEditor insertHtml to wrap element within <p> in webkit browsers?

Im trying to build a front-end page to allow my users to build smarty templates with ckeditor wysiwyg editor.
Im using the insertHtml function to add a button with special attributes (needed to parse it into an smarty variable in the back-end):
// initialize ckeditor
$('textarea.editor').ckeditor({
contentsCss: '/css/test.css'
});
// get ckeditor instance
ckeditorInstance = $('textarea.editor').ckeditorGet();
// Use some elements (outside the textarea) to add buttons/tokens
// to wysiwyg textarea
$("a.tinymce.tinymce-insert-var").click(function(){
ckeditorInstance.insertHtml(
'<input type="button" readonly="readonly" var="{$user->name}" '
+ 'class="placeholder" value="User Name" />'
);
});
This works fine on Firefox, IE8 and opera, but with Chrome/Chromium/Safari the button is inserted between a <p> element.
Is there a way to avoid this, or a callback that i can use to remove the paragraph?
I had this problem as well. This is how I did it...
var editor = $('textarea[name=content]').ckeditorGet();
var element = CKEDITOR.dom.element.createFromHtml( '<p>I am a new paragraph</p>' );
editor.insertElement( element );
Looks like you're using jQuery also... why don't you force the inclusion of the p tag within CKEditor's .insertHtml function, then follow it up with jQuery's .unwrap to always remove the p tags?
in the main ckeditor config-file there is an option to disable automatic <p> inserts.
try to change the value of CKConfig.EnterMode and CKConfig.ShiftEnterMode for example to 'br'.
Felix