Trick to expand Xamarin Form WebView as per dynamic content - xamarin.ios

I have a WebView in my project. It can have dynamic html content. For now i have given fixed width and height to WebView and it scrolls. But i want to remove scroll by increasing height of WebView dynamically.
Is there any way like by creating custom renderer or something?
Sample code
var webvw = new Webview();
var htmlSource = new HtmlWebViewSource();
htmlSource.Html = #"<html>" +
"<head>" +
"<style type=\"text/css\">" +
"#font-face {" +
"font-family: Roboto-Medium;" + fntsrc + "}" +
"html,body{margin:0px;}" +
"body {" +
"font-family: Roboto-Medium;" +
"font-size: 12px" +
"text-align: left;" +
"color: #acacac;" + "}" +
"body :first-child{" +
"font-family: Roboto-Medium;" +
"font-size: 12px" +
"font-weight: 300;" +
"line-height: 24px;" +
"text-align: left;" +
"color: #ffffff;" + "}" +
"</style>" +
"</head>" +
"<body style=\"background-color: transparent;\" >" +
dynamicContent + "</body>" + "</html>";
webvw.Source = htmlSource;
webvw.WidthRequest = 500;
webvw.HeightRequest = 500;
SatackLayout webContnet=new StackLayout{
VerticalOptions=LayoutOption.FillAndExpand,
Orientation=StackOrientation.Vertical
};

There is a way but it is complicated. The WebView won't automatically size to its content, so the only way you could do it is if the content notifies your code how big it is.
To do this you will need to Invoke C# from Javascript.
Its a mildly complex procedure and you will need a CustomRenderer and also setup properties in each of the native projects. Follow the link above for a step by step guide on how to do it.
The Javascript you invoke something like this to get the height
var body = document.body,
html = document.documentElement;
var height = Math.max( body.scrollHeight, body.offsetHeight,
html.clientHeight, html.scrollHeight, html.offsetHeight );
Then when its returned back, set your WebView to that height. You may also need to wait until the NavigationCompleted Event is raised before doing this to ensure the contents have loaded in your WebView.

ok here is my "if it looks stupid but works it ain't stupid"-answer.
i run into the same problem and searched for a way to get the possible height.
my solutions is now to create a lable with costum renderes to convert the html code. the label has a property for height and width ;)
so i create the label, put it in a StackLayout(it needs to be rendered), get the size to the WebView, remove the label from the StackLayout and add now the WebView with a perfect size :)
webView = new WebView();
var htmlSource = new HtmlWebViewSource();
htmlSource.Html = htmlCode;
webView.Source = htmlSource;
tmpLable = new HyperLinkLabel {
Text = htmlCode,
};
stackLayout.Children.Add(tmpLable);
webView.WidthRequest = tmpLable.Width;
webView.HeightRequest = tmpLable.Height;
stackLayout.Children.Remove(text);
stackLayout.Children.Add(web);

Related

KonvaJS, positioning editable text inputs

I need to position text inputs at various places on a KonvaJS layer. I found the following code at https://konvajs.github.io/docs/sandbox/Editable_Text.html and I'm trying to understand the textPosition, stageBox, and areaPosition vars in this code. I want my stage centered in the browser window, but when I do that, the textarea (activated on dblclick) pops up way off to the left. I can't get a console readout of the x/y coordinates, so I can't visualize how the positioning works &, thus, how to change it. Can anyone explain, or point me in the right direction?
var text_overlay = new Konva.Layer();
stage.add(text_overlay);
var textNode = new Konva.Text({
text: 'Some text here',
x: 20,
y: 50,
fontSize: 20
});
text_overlay.add(textNode);
text_overlay.draw();
textNode.on('dblclick', () => {
// create textarea over canvas with absolute position
// first we need to find its position
var textPosition = textNode.getAbsolutePosition();
var stageBox = stage.getContainer().getBoundingClientRect();
var areaPosition = {
x: textPosition.x + stageBox.left,
y: textPosition.y + stageBox.top
};
// create textarea and style it
var textarea = document.createElement('textarea');
document.body.appendChild(textarea);
textarea.value = textNode.text();
textarea.style.position = 'absolute';
textarea.style.top = areaPosition.y + 'px';
textarea.style.left = areaPosition.x + 'px';
textarea.style.width = textNode.width();
textarea.focus();
textarea.addEventListener('keydown', function (e) {
// hide on enter
if (e.keyCode === 13) {
textNode.text(textarea.value);
text_overlay.draw();
document.body.removeChild(textarea);
}
});
})
// add the layer to the stage
stage.add(text_overlay);
UPDATE: I solved part of the problem--the textarea showing up way out of position. You need to use 2 divs in the HTML file instead of one, like so:
<div id="containerWrapper" align="center"><div id="container"></div></div>
Thanks to Frens' answer on Draw border edges of the Konvajs container Stage in html for that one!

Hover Text effect next to mouse cursor

Dear community is there any way to do a text next to the cursor hover effect (in css?) like on this site here?
http://manuelraeder.co.uk/
I tried it with abbr and span style, but it doesn't seem to work. Text should be changeable with every picture.
Thanks in advance!
From the website you linked, they appear to be using Javascript. I don't think there is a way to do this purely with CSS.
When you hover your mouse over an image on the website, a new HTML tag is created at the end of the body:
<p class="tooltip" style="display: block; top: ...; left: ...;">TEXT</p>
Where top and left correspond to the pixel values that your cursor is at, and the text would be whatever text you want to float next to the cursor.
In the Javascript, you would create a hover observer for the associated images, and inside the trigger function create the new p tooltip element. You would set the text for your p element to be the respective image's alt title. Looking at the website's Javascript, this is what they did for their tooltip:
$(document).ready(function() {
// Tooltip only Text
$('.masterTooltip').hover(function(){
// Hover over code
var title = $(this).attr('title');
$(this).data('tipText', title).removeAttr('title');
$('<p class="tooltip"></p>')
.text(title)
.appendTo('body')
.fadeIn('fast');
}, function() {
// Hover out code
$(this).attr('title', $(this).data('tipText'));
$('.tooltip').remove();
}).mousemove(function(e) {
var mousex = e.pageX + 20; //Get X coordinates
var mousey = e.pageY + 10; //Get Y coordinates
$('.tooltip')
.css({ top: mousey, left: mousex })
});
});

how to translate a dynamically added SVG animation on jointjs when a paper is scaled

I am not able to figure out how to re position an svg animation that i add dynamically on my paper during a zoom in or zoom out.
I add the animation when the link is active according to business logic in the following way.
c = joint.V('circle', { r: 8, fill: 'green' });
c.animateAlongPath({ dur: '4s', repeatCount: 'indefinite' }, canvasPaper.findViewByModel(link).$('.connection')[0]);
joint.V(canvasPaper.svg).append(c)
Now i go to the canvas and zoom in or zoom out the elements in the canvas scale appropriately . i use the paper.scale command. But the animation that i added does not move. I was able to get it scaled down to size but not its position. How do i achieve this?.
My zoom in and zoom out code is as below. I also know that i have to use the translate command on the svg object but i do not know how to calculate the translate values based on the zoomLevel
$('#zoom-in').on('click', function(e) {
e.preventDefault();
zoomLevel = Number((Math.min(1, zoomLevel + 0.2)).toFixed(1));
canvasPaper.scale(zoomLevel, zoomLevel,0,0);
_.each(canvasGraph.getLinks(), function(link) {
if(link.attr('linkActiveAnimationSvgId/text')) {document.getElementById(link.attr('linkActiveAnimationSvgId/text')).setAttribute("transform", "scale(" + zoomLevel + "," + zoomLevel + ")")
}
})
})
My zoom out code is as below
$('#zoom-out').on('click', function(e) {
e.preventDefault();
zoomLevel =Number((Math.max(0.2, zoomLevel - 0.2)).toFixed(1));
canvasPaper.scale(zoomLevel, zoomLevel,0,0);
_.each(canvasGraph.getLinks(), function(link) {
if(link.attr('linkActiveAnimationSvgId/text')) {document.getElementById(link.attr('linkActiveAnimationSvgId/text')).setAttribute("transform", "scale(" + zoomLevel + "," + zoomLevel + ")")
}
})
})
ok all i had to do was to find the view of the paper and then
paperView.vel.append(c)
instead of
joint.V(canvasPaper.svg).append(c)
and now i scale the paper and the animation scales/translates appropriately

MVC 5 action link text change to image

this is action links code in mvc 5. I need to add images instead of text. how to do it
#Html.Raw("<a onclick='MergeCustomer(" + item.customer_id + ", " +
TempData["NewCustomerID"] + ")'>Merge</a>")
<span style=" color:black">|</span>
#Ajax.ActionLink("Compare", "_CompareCustomerDetails",
new { ExistingCustomerId = item.customer_id, NewCustomerId = TempData["NewCustomerID"]},
new AjaxOptions()
{
HttpMethod = "Get",
UpdateTargetId =divCustomerCompare",
InsertionMode = InsertionMode.Replace
}, new { id = "lnkCompare"})}
You can't. #Html.ActionLink only works on text.
In this instance your best bet is to use the #Url.Action() helper method, like so:
<img src="yourimage.jpg"/>

Convert SVG to PNG and maintain CSS integrity

I am currently using canvg() and Canvas2Image to copy my SVG to a canvas and then convert the canvas to PNG. I would like to maintain the image format and not use PDF.
How can I maintain the CSS integrity? Chart is made using NVD3.js.
downloadPhoto: function() {
var chartArea = document.getElementsByTagName('svg')[0].parentNode;
var svg = chartArea.innerHTML;
var canvas = document.createElement('canvas');
canvas.setAttribute('width', chartArea.offsetWidth);
canvas.setAttribute('height', chartArea.offsetHeight);
canvas.setAttribute('display', 'none');
canvas.setAttribute(
'style',
'position: absolute; ' +
'top: ' + (-chartArea.offsetHeight * 2) + 'px;' +
'left: ' + (-chartArea.offsetWidth * 2) + 'px;');
document.body.appendChild(canvas);
canvg(canvas, svg);
Canvas2Image.saveAsPNG(canvas);
canvas.parentNode.removeChild(canvas);
}
Style definitions for svg elements defined in stylesheets are not applied to the generated canvas. This can be patched by adding style definitions to the svg elements before calling canvg.
Inspired on this article, I've created this:
function generateStyleDefs(svgDomElement) {
var styleDefs = "";
var sheets = document.styleSheets;
for (var i = 0; i < sheets.length; i++) {
var rules = sheets[i].cssRules;
for (var j = 0; j < rules.length; j++) {
var rule = rules[j];
if (rule.style) {
var selectorText = rule.selectorText;
var elems = svgDomElement.querySelectorAll(selectorText);
if (elems.length) {
styleDefs += selectorText + " { " + rule.style.cssText + " }\n";
}
}
}
}
var s = document.createElement('style');
s.setAttribute('type', 'text/css');
s.innerHTML = "<![CDATA[\n" + styleDefs + "\n]]>";
//somehow cdata section doesn't always work; you could use this instead:
//s.innerHTML = styleDefs;
var defs = document.createElement('defs');
defs.appendChild(s);
svgDomElement.insertBefore(defs, svgDomElement.firstChild);
}
// generate style definitions on the svg element(s)
generateStyleDefs(document.getElementById('svgElementId'));
The key thing here is that all the style rules need to be part of the SVG, not in external style files. So you would need to go through all the CSS for NVD3 and set all of those attributes in the code. Anything that is set via an external stylesheet will be ignored.
just to make #Lars Kotthoff's answer more concrete. "example of how to export a png directly from an svg" has a working example. the code snippet/gist tries to first apply all css to the svg inline and then draw the image on the canvas and export the data as png. (internally it adopted svg-crowbar code). and i apply the technique in my project and it works smoothly - a download button that can download the svg image rendered using nvd3.

Resources