Commit a3e00954 authored by jan.koester's avatar jan.koester
Browse files

hover effefts and section slect button

parent 00978c5c
Loading
Loading
Loading
Loading
+4 −0
Original line number Diff line number Diff line
@@ -417,6 +417,10 @@ var EditorApi = (function() {
            return request('GET', '/api/document/export-html');
        },

        listSections: function() {
            return request('GET', '/api/document/sections');
        },

        // Survey management
        listSurveys: function() {
            return request('GET', '/api/surveys');
+19 −1
Original line number Diff line number Diff line
@@ -357,7 +357,25 @@ var PropertiesPanel = (function() {
                group.appendChild(label);

                var input;
                if (field.type === 'survey_select') {
                if (field.type === 'section_select') {
                    input = document.createElement('select');
                    input.name = field.key;
                    var emptyOptSec = document.createElement('option');
                    emptyOptSec.value = '';
                    emptyOptSec.textContent = '-- Abschnitt wählen --';
                    input.appendChild(emptyOptSec);
                    (function(sel, curVal) {
                        EditorApi.listSections().then(function(resp) {
                            (resp.sections || []).forEach(function(s, idx) {
                                var o = document.createElement('option');
                                o.value = s.uuid;
                                o.textContent = s.css_class ? s.css_class : ('Section ' + (idx + 1));
                                if (curVal === s.uuid) o.selected = true;
                                sel.appendChild(o);
                            });
                        }).catch(function() {});
                    })(input, value);
                } else if (field.type === 'survey_select') {
                    input = document.createElement('select');
                    input.name = field.key;
                    var emptyOptS = document.createElement('option');
+58 −0
Original line number Diff line number Diff line
@@ -769,6 +769,12 @@ bool webedit::Api::handleRequest(libhttppp::HttpRequest &curreq, const int tid,
        return true;
    }

    // Route: /api/document/sections (GET) — lightweight section list for button section_select
    if (path == "/api/document/sections") {
        handleListDocumentSections(curreq, sessionid);
        return true;
    }

    // Route: /api/survey/names (GET) — lightweight list for widget dropdown
    if (path == "/api/survey/names") {
        handleListSurveyNames(curreq, sessionid);
@@ -4104,6 +4110,58 @@ void webedit::Api::handleListSurveys(libhttppp::HttpRequest &curreq,
    json_object_put(resp);
}

static void collectSections(const blogi::webedit::EditPlugin *node, json_object *arr) {
    while (node) {
        if (node->getName() == "Section") {
            json_object *reqJson  = json_object_new_object();
            json_object *respJson = json_object_new_object();
            json_object_object_add(reqJson, "action", json_object_new_string("read"));
            const_cast<blogi::webedit::EditPlugin*>(node)->JsonApi(reqJson, respJson);

            std::string cssClass;
            json_object *dataObj = nullptr;
            if (json_object_object_get_ex(respJson, "data", &dataObj)) {
                json_object *propsStr = nullptr;
                if (json_object_object_get_ex(dataObj, "properties", &propsStr)) {
                    json_object *props = json_tokener_parse(json_object_get_string(propsStr));
                    if (props) {
                        json_object *ccObj = nullptr;
                        if (json_object_object_get_ex(props, "css_class", &ccObj)) {
                            const char *cc = json_object_get_string(ccObj);
                            if (cc && cc[0]) cssClass = cc;
                        }
                        json_object_put(props);
                    }
                }
            }
            json_object_put(reqJson);
            json_object_put(respJson);

            json_object *entry = json_object_new_object();
            json_object_object_add(entry, "uuid", json_object_new_string(node->getInstanceId().c_str()));
            json_object_object_add(entry, "css_class", json_object_new_string(cssClass.c_str()));
            json_object_array_add(arr, entry);
        }
        if (node->getChildElement())
            collectSections(node->getChildElement(), arr);
        node = node->nextElement();
    }
}

void webedit::Api::handleListDocumentSections(libhttppp::HttpRequest &curreq,
                                               const std::string &sessionid) {
    auto &doc = getDocState(sessionid);
    std::lock_guard<std::mutex> lk(doc.mtx);

    json_object *arr  = json_object_new_array();
    collectSections(doc.root, arr);

    json_object *resp = json_object_new_object();
    json_object_object_add(resp, "sections", arr);
    sendJson(curreq, resp);
    json_object_put(resp);
}

void webedit::Api::handleListSurveyNames(libhttppp::HttpRequest &curreq,
                                          const std::string &sessionid) {
    std::string uid;
+3 −0
Original line number Diff line number Diff line
@@ -145,6 +145,9 @@ namespace webedit {
        std::mutex _connSessionMtx;
        std::map<std::string, ConnSession> _connSessions;

        // Document section list (for section_select widget field)
        void handleListDocumentSections(libhttppp::HttpRequest &curreq, const std::string &sessionid);

        // Survey management handlers
        void handleListSurveys(libhttppp::HttpRequest &curreq, const std::string &sessionid);
        void handleListSurveyNames(libhttppp::HttpRequest &curreq, const std::string &sessionid);
+67 −0
Original line number Diff line number Diff line
@@ -73,6 +73,12 @@ extern "C" {
            bool hidden = false;
            bool m_hidden = false;

            // Hover effect
            std::string hoverEffect     = "none";   // none, move_up, glow, scale, fade, move_up_glow
            std::string hoverBgColor    = "";
            std::string hoverTextColor  = "";
            std::string hoverTransition = "0.2s ease";

            // Custom CSS
            std::string customCss = "";

@@ -375,6 +381,11 @@ extern "C" {
                    json_object *hf = json_object_array_get_idx(arr, json_object_array_length(arr) - 1);
                    json_object_object_add(hf, "default", json_object_new_boolean(false));
                }
                addField("hover_effect", "Hover Effect", "select", nullptr, "desktop",
                         mkOpts({"none","move_up","glow","scale","fade","move_up_glow"}));
                addField("hover_bg_color", "Hover Background Color", "color_var", nullptr, "desktop");
                addField("hover_text_color", "Hover Text Color", "color_var", nullptr, "desktop");
                addField("hover_transition", "Hover Transition", "text", "0.2s ease", "desktop");
                addField("custom_css", "Custom CSS", "textarea", ".we-xxx { color: red; }");
                addField("g_event_enabled", "Enable Google Event", "checkbox");
                addField("g_event_name", "Event Name", "text", "button_click", "all", nullptr, mkVisible("g_event_enabled", "true"));
@@ -430,6 +441,12 @@ extern "C" {
                element->SetAttribute("g_event_value", gEventValue.c_str());
                element->SetAttribute("g_consent_update", gConsentUpdate ? "true" : "false");

                // Hover effect
                element->SetAttribute("hover_effect", hoverEffect.c_str());
                element->SetAttribute("hover_bg_color", hoverBgColor.c_str());
                element->SetAttribute("hover_text_color", hoverTextColor.c_str());
                element->SetAttribute("hover_transition", hoverTransition.c_str());

                if (!customCss.empty()) {
                    tinyxml2::XMLElement* cssEl = doc->NewElement("CustomCss");
                    cssEl->SetText(customCss.c_str());
@@ -499,6 +516,16 @@ extern "C" {
                val = xml_data->Attribute("g_consent_update");
                if (val) gConsentUpdate = (strcmp(val, "true") == 0);

                // Hover effect
                val = xml_data->Attribute("hover_effect");
                if (val) hoverEffect = val;
                val = xml_data->Attribute("hover_bg_color");
                if (val) hoverBgColor = val;
                val = xml_data->Attribute("hover_text_color");
                if (val) hoverTextColor = val;
                val = xml_data->Attribute("hover_transition");
                if (val && val[0]) hoverTransition = val;

                tinyxml2::XMLElement* cssEl = xml_data->FirstChildElement("CustomCss");
                if (cssEl) {
                    const char* cssVal = cssEl->GetText();
@@ -534,6 +561,10 @@ extern "C" {
                json_object_object_add(obj, "m_height", json_object_new_string(m_height.c_str()));
                json_object_object_add(obj, "hidden", json_object_new_boolean(hidden));
                json_object_object_add(obj, "m_hidden", json_object_new_boolean(m_hidden));
                json_object_object_add(obj, "hover_effect", json_object_new_string(hoverEffect.c_str()));
                json_object_object_add(obj, "hover_bg_color", json_object_new_string(hoverBgColor.c_str()));
                json_object_object_add(obj, "hover_text_color", json_object_new_string(hoverTextColor.c_str()));
                json_object_object_add(obj, "hover_transition", json_object_new_string(hoverTransition.c_str()));
                json_object_object_add(obj, "custom_css", json_object_new_string(customCss.c_str()));
                json_object_object_add(obj, "g_event_enabled", json_object_new_boolean(gEventEnabled));
                json_object_object_add(obj, "g_event_name", json_object_new_string(gEventName.c_str()));
@@ -643,6 +674,18 @@ extern "C" {
                        m_hidden = json_object_get_boolean(val_obj);
                    }
                }
                if (json_object_object_get_ex(obj, "hover_effect", &val_obj)) {
                    val = json_object_get_string(val_obj); if (val) hoverEffect = val;
                }
                if (json_object_object_get_ex(obj, "hover_bg_color", &val_obj)) {
                    val = json_object_get_string(val_obj); if (val) hoverBgColor = val;
                }
                if (json_object_object_get_ex(obj, "hover_text_color", &val_obj)) {
                    val = json_object_get_string(val_obj); if (val) hoverTextColor = val;
                }
                if (json_object_object_get_ex(obj, "hover_transition", &val_obj)) {
                    val = json_object_get_string(val_obj); if (val && val[0]) hoverTransition = val;
                }
                if (json_object_object_get_ex(obj, "custom_css", &val_obj)) {
                    val = json_object_get_string(val_obj);
                    if (val) customCss = val;
@@ -758,6 +801,8 @@ extern "C" {
                style += " text-decoration: none; cursor: pointer;";
                if (!width.empty()) style += " width: " + width + ";";
                if (!height.empty()) style += " height: " + height + ";";
                if (hoverEffect != "none")
                    style += " transition: all " + hoverTransition + ";";
                if (hidden) style += " display: none;";

                a.setAttribute("style", style.c_str());
@@ -783,7 +828,29 @@ extern "C" {
                if (!ml_backgroundColor.empty()) mobileLightCSS += " background-color: " + ml_backgroundColor + " !important;";
                if (!ml_textColor.empty()) mobileLightCSS += " color: " + ml_textColor + " !important;";

                // Hover effect CSS
                std::string hoverCSS;
                if (hoverEffect != "none") {
                    std::string hoverProps;
                    if (hoverEffect == "move_up" || hoverEffect == "move_up_glow")
                        hoverProps += " transform: translateY(-4px);";
                    if (hoverEffect == "scale")
                        hoverProps += " transform: scale(1.05);";
                    if (hoverEffect == "fade")
                        hoverProps += " opacity: 0.75;";
                    if (hoverEffect == "glow" || hoverEffect == "move_up_glow")
                        hoverProps += " box-shadow: 0 0 16px 4px " + backgroundColor + ";";
                    if (!hoverBgColor.empty())
                        hoverProps += " background-color: " + hoverBgColor + " !important;";
                    if (!hoverTextColor.empty())
                        hoverProps += " color: " + hoverTextColor + " !important;";
                    if (!hoverProps.empty())
                        hoverCSS = "." + responsiveClass + ":hover {" + hoverProps + " }";
                }

                std::string allMediaCSS;
                if (!hoverCSS.empty())
                    allMediaCSS += hoverCSS + " ";
                if (!mobileCSS.empty()) {
                    allMediaCSS += "@media (max-width: 768px) { ." + responsiveClass + " {" + mobileCSS + " } } ";
                }