Skip to content

Commit

Permalink
Tagbox: support markdown for text in read-only mode (#7569)
Browse files Browse the repository at this point in the history
* resolve #7542 Tagbox: support markdown for text in read-only mode

* work for #7542 fix vue3

---------

Co-authored-by: OlgaLarina <[email protected]>
  • Loading branch information
OlgaLarina and OlgaLarina authored Dec 26, 2023
1 parent 4bee0d5 commit 4e3c445
Show file tree
Hide file tree
Showing 12 changed files with 105 additions and 8 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@
</div>
<sv-ng-popup *ngIf="!model.isReadOnly" [popupModel]="model.popupModel"></sv-ng-popup>
<div disabled *ngIf="model.isReadOnly" [class]="model.getControlClass()" [attr.id]="model.inputId">
<div>{{ model.readOnlyText }}</div>
<sv-ng-string *ngIf="model.locReadOnlyText" [model]="model.locReadOnlyText"></sv-ng-string>
</div>
<div *ngIf="model.cssClasses.chevronButtonIconId" [class]="model.cssClasses.chevronButton" (pointerdown)="chevronPointerDown($event)" aria-hidden="true">
<svg [iconName]="model.cssClasses.chevronButtonIconId" [partCss]="model.cssClasses.chevronButtonSvg" [size]="'auto'" sv-ng-svg-icon></svg>
Expand Down
5 changes: 4 additions & 1 deletion packages/survey-vue3-ui/src/components/tagbox/Tagbox.vue
Original file line number Diff line number Diff line change
Expand Up @@ -57,7 +57,10 @@
:id="question.inputId"
:class="question.getControlClass()"
>
<div>{{ question.readOnlyText }}</div>
<survey-string
v-if="question.locReadOnlyText"
:locString="question.locReadOnlyText"
/>
</div>
<div
:class="question.cssClasses.chevronButton"
Expand Down
5 changes: 4 additions & 1 deletion src/knockout/components/tagbox/tagbox.html
Original file line number Diff line number Diff line change
Expand Up @@ -66,7 +66,10 @@
<!-- /ko -->
<!-- ko if: question.isReadOnly -->
<div disabled data-bind="css: question.getControlClass(), attr: { id: question.inputId }, ">
<div data-bind="text: question.readOnlyText"></div>
<!-- ko if: question.locReadOnlyText -->
<!-- ko template: { name: 'survey-string', data: question.locReadOnlyText } -->
<!-- /ko -->
<!-- /ko -->
</div>
<!-- /ko -->
<!-- ko if: question.cssClasses.chevronButtonIconId -->
Expand Down
12 changes: 11 additions & 1 deletion src/question_tagbox.ts
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ export class QuestionTagboxModel extends QuestionCheckboxModel {
super(name);
this.createLocalizableString("placeholder", this, false, true);
this.createLocalizableString("clearCaption", this, false, true);
this.createLocalizableString("readOnlyText", this, true);
this.registerPropertyChangedHandlers(["value", "renderAs", "showOtherItem", "otherText", "placeholder", "choices", "visibleChoices"], () => {
this.updateReadOnlyText();
});
Expand All @@ -32,7 +33,6 @@ export class QuestionTagboxModel extends QuestionCheckboxModel {
this.updateReadOnlyText();
this.dropdownListModel?.locStrsChanged();
}
@property({ defaultValue: "" }) readOnlyText: string;
private updateReadOnlyText(): void {
this.readOnlyText = this.displayValue || this.placeholder;
}
Expand Down Expand Up @@ -112,6 +112,16 @@ export class QuestionTagboxModel extends QuestionCheckboxModel {
return this.getLocalizableString("clearCaption");
}

public get readOnlyText(): string {
return this.getLocalizableStringText("readOnlyText");
}
public set readOnlyText(val: string) {
this.setLocalizableStringText("readOnlyText", val);
}
get locReadOnlyText(): LocalizableString {
return this.getLocalizableString("readOnlyText");
}

public getType(): string {
return "tagbox";
}
Expand Down
5 changes: 4 additions & 1 deletion src/react/dropdown-base.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,9 @@ export class SurveyQuestionDropdownBase<T extends Question> extends SurveyQuesti
protected getValueCore(): any {
return this.questionBase.renderedValue;
}
protected renderReadOnlyElement(): JSX.Element | null {
return <div>{this.question.readOnlyText}</div>;
}
protected renderSelect(cssClasses: any): JSX.Element {
let selectElement: JSX.Element | null = null;
if (this.question.isReadOnly) {
Expand All @@ -45,7 +48,7 @@ export class SurveyQuestionDropdownBase<T extends Question> extends SurveyQuesti
// @ts-ignore
selectElement = <div id={this.question.inputId} className={this.question.getControlClass()} disabled>
{text}
<div>{this.question.readOnlyText}</div>
{this.renderReadOnlyElement()}
</div>;
} else {
if (!(this.question as any)["dropdownListModel"]) {
Expand Down
8 changes: 8 additions & 0 deletions src/react/reactquestion_tagbox.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -63,6 +63,14 @@ export class SurveyQuestionTagbox extends SurveyQuestionDropdownBase<QuestionTag
</div>
);
}

protected renderReadOnlyElement(): JSX.Element | null {
if(this.question.locReadOnlyText) {
return this.renderLocString(this.question.locReadOnlyText);
} else {
return null;
}
}
}

ReactQuestionFactory.Instance.registerQuestion("tagbox", (props) => {
Expand Down
5 changes: 4 additions & 1 deletion src/vue/components/tagbox/tagbox.vue
Original file line number Diff line number Diff line change
Expand Up @@ -46,7 +46,10 @@
</div>
<sv-popup v-if="!question.isReadOnly" :model="model.popupModel"></sv-popup>
<div disabled v-else :id="question.inputId" :class="question.getControlClass()">
<div>{{ question.readOnlyText }}</div>
<survey-string
v-if="question.locReadOnlyText"
:locString="question.locReadOnlyText"
/>
</div>
<div
:class="question.cssClasses.chevronButton"
Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
<div>
<div class="sv_q_tagbox_wrapper sv_select_wrapper">
<div class="sv_q_dropdown_control sv_q_input sv_q_tagbox" disabled="" id="testid0i">
<div>item1, item3</div>
<span class="sv-string-viewer">item1, item3</span>
</div>
</div>
</div>
2 changes: 1 addition & 1 deletion tests/markup/snapshots/tagbox-readonly.snap.html
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
<div>
<div class="sv_q_tagbox_wrapper sv_select_wrapper">
<div class="sv_q_dropdown_control sv_q_dropdown--empty sv_q_input sv_q_tagbox sv_q_tagbox--empty" disabled="" id="testid0i">
<div>Select...</div>
<span class="sv-string-viewer">Select...</span>
</div>
</div>
</div>
28 changes: 28 additions & 0 deletions tests/question_tagbox_tests.ts
Original file line number Diff line number Diff line change
Expand Up @@ -1480,4 +1480,32 @@ QUnit.test("Can clear tagbox value", assert => {
row.showDetailPanel();
const question = row.getQuestionByName("detailTypes");
assert.ok(question, "There is no exception");
});

QUnit.test("Check readOnly tagbox with markdown", function (assert) {
const survey = new SurveyModel({
elements: [
{
type: "tagbox",
name: "q1",
choices: [
"item1",
"item2",
"item3",
"item4"
]
}
]
});
survey.onGetQuestionDisplayValue.add((sender, options) => {
const strs = options.displayValue.split(",");
options.displayValue = strs.join(" | ");
});
const q1 = survey.getQuestionByName("q1") as QuestionTagboxModel;

survey.mode = "display";
survey.data = { q1: ["item1", "item2", "item3"] };

assert.equal(q1.displayValue, "item1 | item2 | item3");
assert.equal(q1.locReadOnlyText.renderedHtml, "item1 | item2 | item3");
});
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
39 changes: 39 additions & 0 deletions visualRegressionTests/tests/defaultV2/tagbox.ts
Original file line number Diff line number Diff line change
Expand Up @@ -441,4 +441,43 @@ frameworks.forEach(async framework => {
await takeElementScreenshot("tagbox-contrast-input.png", Selector(".sd-question"), t, comparer);
});
});

test("Check readOnly tagbox with markdown", async (t) => {
await wrapVisualTest(t, async (t, comparer) => {
await t.resizeWindow(900, 400);

await initSurvey(framework, {
focusFirstQuestionAutomatic: true,
showQuestionNumbers: "off",
mode: "display",
questions: [
{
type: "tagbox",
name: "q1",
defaultValue: ["Cuba", "Romania"],
choicesByUrl: {
url: "http://127.0.0.1:8080/testCafe/countriesMock.json",
path: "RestResponse;result",
valueName: "name",
},
}
]
}, {
"onGetQuestionDisplayValue": (sender, options) => {
var strs = options.displayValue.split(",");
options.displayValue = strs.join("<br>");
},
"onTextMarkdown": (survey, options) => {
var converter = new window["showdown"].Converter();
var str = converter.makeHtml(options.text);
str = str.substring(3);
str = str.substring(0, str.length - 4);
options.html = str;
}
});

const question = Selector(".sd-input.sd-tagbox");
await takeElementScreenshot("tagbox-readonly-with-markdown.png", question, t, comparer);
});
});
});

0 comments on commit 4e3c445

Please sign in to comment.