Sun, 07 Dec 2025 20:00:33 +0100
fix settings dialog doesn't open when there is no .dav/config.xml file
/* * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER. * * Copyright 2025 Olaf Wintermann. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE * POSSIBILITY OF SUCH DAMAGE. */ #import "webview.h" #import "Container.h" UIWIDGET ui_webview_create(UiObject *obj, UiWebviewArgs *args) { UiVar *var = uic_widget_var(obj->ctx, obj->ctx, args->value, args->varname, UI_VAR_GENERIC); WKWebView *webview = [[WKWebView alloc]init]; UiLayout layout = UI_ARGS2LAYOUT(args); ui_container_add(obj, webview, &layout); if(var) { UiGeneric *value = var->value; value->get = ui_webview_get; value->get_type = ui_webview_get_type; value->set = ui_webview_set; value->destroy = ui_webview_destroy; value->obj = (__bridge void*)webview; if(value->value) { ui_webview_set(value, value->value, UI_WEBVIEW_OBJECT_TYPE); } else { UiWebViewData *data = malloc(sizeof(UiWebViewData)); memset(data, 0, sizeof(UiWebViewData)); data->webview = (__bridge void*)webview; data->javascript = TRUE; data->zoom = 1; value->value = value; } } return (__bridge void*)webview; } UiWebViewData* ui_webview_data_clone(UiWebViewData *data) { UiWebViewData *newdata = malloc(sizeof(UiWebViewData)); memset(newdata, 0, sizeof(UiWebViewData)); newdata->zoom = 1; newdata->javascript = TRUE; if(data) { newdata->uri = data->uri ? strdup(data->uri) : NULL; newdata->mimetype = data->mimetype ? strdup(data->mimetype) : NULL; newdata->encoding = data->encoding ? strdup(data->encoding) : NULL; newdata->type = data->type; newdata->javascript = data->javascript; newdata->zoom = data->zoom; if(data->content && data->contentlength > 0) { newdata->content = malloc(data->contentlength + 1); memcpy(newdata->content, data->content, data->contentlength); newdata->content[data->contentlength] = 0; newdata->contentlength = data->contentlength; } } return newdata; } void ui_webview_data_free(UiWebViewData *data) { if(!data) { return; } free(data->uri); free(data->mimetype); free(data->encoding); free(data->content); free(data); } void* ui_webview_get(UiGeneric *g) { UiWebViewData *data = g->value; WKWebView *webview = (__bridge WKWebView*)g->obj; if(data->type == WEBVIEW_CONTENT_URL) { (void)ui_webview_get_uri(g); // this updates data->uri } data->zoom = webview.pageZoom; return ui_webview_data_clone(g->value); } const char* ui_webview_get_type(UiGeneric *g) { return UI_WEBVIEW_OBJECT_TYPE; } int ui_webview_set(UiGeneric *g, void *data, const char *type) { if(!data || !type) { return 1; } if(strcmp(type, UI_WEBVIEW_OBJECT_TYPE)) { return 1; } ui_webview_data_free(g->value); g->value = ui_webview_data_clone(data); WKWebView *webview = (__bridge WKWebView*)g->obj; UiWebViewData *webd = data; if(webd->type == WEBVIEW_CONTENT_URL) { const char *uri = webd->uri ? webd->uri : "about:blank"; NSURL *url = [NSURL URLWithString:[[NSString alloc] initWithUTF8String:uri]]; if(url) { NSURLRequest *req = [NSURLRequest requestWithURL:url]; if(req) { [webview loadRequest:req]; } } } else { NSString *mimetype = [[NSString alloc]initWithUTF8String: webd->mimetype ? webd->mimetype : "text/plain"]; NSString *encoding = [[NSString alloc]initWithUTF8String: webd->encoding ? webd->encoding : "UTF-8"]; NSString *urlStr = [[NSString alloc]initWithUTF8String: webd->uri ? webd->uri : "file:///"]; NSURL *url = [NSURL URLWithString:urlStr]; NSData *content = [NSData dataWithBytes:webd->content length:webd->contentlength]; if(!url) { url = [NSURL URLWithString:@"about:blank"]; } [webview loadData:content MIMEType:mimetype characterEncodingName:encoding baseURL:url]; } webview.pageZoom = webd->zoom; return 1; } void ui_webview_destroy(UiGeneric *g) { ui_webview_data_free(g->value); g->value = NULL; } void ui_webview_load_url(UiGeneric *g, const char *url) { WKWebView *webview = (__bridge WKWebView*)g->obj; UiWebViewData *data = g->value; data->type = WEBVIEW_CONTENT_URL; if(!url) { url = "about:blank"; } NSURL *nsurl = [NSURL URLWithString:[[NSString alloc] initWithUTF8String:url]]; if(nsurl) { NSURLRequest *req = [NSURLRequest requestWithURL:nsurl]; if(req) { [webview loadRequest:req]; } } } void ui_webview_load_content( UiGeneric *g, const char *uri, const char *content, size_t contentlength, const char *mimetype, const char *encoding) { UiWebViewData *data = g->value; WKWebView *webview = (__bridge WKWebView*)g->obj; data->type = WEBVIEW_CONTENT_CONTENT; free(data->uri); data->uri = NULL; free(data->mimetype); free(data->encoding); free(data->content); data->type = WEBVIEW_CONTENT_URL; data->content = malloc(contentlength+1); memcpy(data->content, content, contentlength); data->content[contentlength] = 0; if(!mimetype) { mimetype = "text/plain"; } if(!encoding) { encoding = "UTF-8"; } data->mimetype = strdup(mimetype); data->encoding = strdup(encoding); NSString *mtype = [[NSString alloc]initWithUTF8String:mimetype]; NSString *enc = [[NSString alloc]initWithUTF8String:encoding]; NSData *ct = [NSData dataWithBytes:content length:contentlength]; NSURL *url; if(uri) { NSString *uriStr = [[NSString alloc]initWithUTF8String:uri]; url = [NSURL URLWithString:uriStr]; } else { url = [NSURL URLWithString:@"file:///"]; } [webview loadData:ct MIMEType:mtype characterEncodingName:enc baseURL:url]; } void ui_webview_reload(UiGeneric *g) { WKWebView *webview = (__bridge WKWebView*)g->obj; [webview reload]; } UiBool ui_webview_can_go_back(UiGeneric *g) { return FALSE; } UiBool ui_webview_can_go_forward(UiGeneric *g) { return FALSE; } void ui_webview_go_back(UiGeneric *g) { } void ui_webview_go_forward(UiGeneric *g) { } const char * ui_webview_get_uri(UiGeneric *g) { UiWebViewData *data = g->value; WKWebView *webview = (__bridge WKWebView*)g->obj; free(data->uri); data->uri = NULL; NSURL *url = webview.URL; if(url) { NSString *s = [url absoluteString]; if(s) { data->uri = strdup(s.UTF8String); } } return data->uri; } void ui_webview_enable_javascript(UiGeneric *g, UiBool enable) { // unsupported } void ui_webview_set_zoom(UiGeneric *g, double zoom) { WKWebView *webview = (__bridge WKWebView*)g->obj; webview.pageZoom = zoom; } double ui_webview_get_zoom(UiGeneric *g) { WKWebView *webview = (__bridge WKWebView*)g->obj; return webview.pageZoom; }