diff --git a/.storybook/stories/file-input/advanced-file-input-states.stories.ts b/.storybook/stories/file-input/advanced-file-input-states.stories.ts
new file mode 100644
index 0000000000..62f57b7848
--- /dev/null
+++ b/.storybook/stories/file-input/advanced-file-input-states.stories.ts
@@ -0,0 +1,153 @@
+/*
+ * Copyright (c) 2016-2024 Broadcom. All Rights Reserved.
+ * The term "Broadcom" refers to Broadcom Inc. and/or its subsidiaries.
+ * This software is released under MIT license.
+ * The full license information can be found in LICENSE in the root directory of this project.
+ */
+
+import { FormsModule } from '@angular/forms';
+import { ClrFileInputModule, ClrFormLayout, ClrFormsModule } from '@clr/angular';
+import { moduleMetadata, StoryContext, StoryFn, StoryObj } from '@storybook/angular';
+
+import { clearFiles, selectFiles } from '../../../projects/angular/src/forms/file-input/file-input.helpers';
+
+export default {
+ title: 'File Input/Advanced File Input States',
+ decorators: [
+ moduleMetadata({
+ imports: [FormsModule, ClrFormsModule, ClrFileInputModule],
+ }),
+ ],
+ argTypes: {
+ // form inputs
+ clrLayout: { control: false },
+ },
+};
+
+const advancedFileInputStatesTemplate: StoryFn = args => ({
+ template: `
+
+ `,
+ props: { ...args },
+});
+
+function advancedFileInputTemplateFn(label: string) {
+ const id = `${label.toLowerCase().replace(/\s+/g, '-')}-file-input`;
+ const ngModel = `${label[0].toLowerCase()}${label.substring(1).replace(/\s+/g, '')}File`;
+
+ return `
+
+
+
+ Helper text for file input control
+ Success message for file input control
+ Required
+ Error message for file input control
+
+
+
+
+ Info text for {{ file.name }}
+ Success message for {{ file.name }}
+ File type not accepted
+ File size too small
+ File size too large
+
+
+
+`;
+}
+
+export const VerticalAdvancedFileInputStates: StoryObj = {
+ render: advancedFileInputStatesTemplate,
+ play: fileInputStatesPlayFn,
+ args: {
+ clrLayout: ClrFormLayout.VERTICAL,
+ },
+};
+
+export const HorizontalAdvancedFileInputStates: StoryObj = {
+ render: advancedFileInputStatesTemplate,
+ play: fileInputStatesPlayFn,
+ args: {
+ clrLayout: ClrFormLayout.HORIZONTAL,
+ },
+};
+
+export const CompactAdvancedFileInputStates: StoryObj = {
+ render: advancedFileInputStatesTemplate,
+ play: fileInputStatesPlayFn,
+ args: {
+ clrLayout: ClrFormLayout.COMPACT,
+ },
+};
+
+function fileInputStatesPlayFn({ canvasElement }: StoryContext) {
+ const successStateFileInputElement = canvasElement.querySelector('#success-state-file-input');
+ selectFiles(successStateFileInputElement, [new File(['.'.repeat(50)], 'file.txt')]);
+
+ const emptyErrorStateFileInputElement = canvasElement.querySelector(
+ '#empty-error-state-file-input'
+ );
+ selectFiles(emptyErrorStateFileInputElement, [new File([''], 'file.txt')]);
+ clearFiles(emptyErrorStateFileInputElement);
+
+ const multipleFilesSuccessStateFileInputElement = canvasElement.querySelector(
+ '#multiple-files-success-state-file-input'
+ );
+ selectFiles(multipleFilesSuccessStateFileInputElement, [
+ new File(['.'.repeat(50)], 'file-1.txt'),
+ new File(['.'.repeat(50)], 'file-2.txt'),
+ new File(['.'.repeat(50)], 'file-3.txt'),
+ ]);
+
+ const multipleFilesErrorStateFileInputElement = canvasElement.querySelector(
+ '#multiple-files-error-state-file-input'
+ );
+ selectFiles(multipleFilesErrorStateFileInputElement, [
+ new File(['.'.repeat(25)], 'file-1.txt'),
+ new File(['.'.repeat(501)], 'file-2.txt'),
+ new File(['.'.repeat(50)], 'file-3.png'),
+ ]);
+
+ const multipleFilesMixedStateFileInputElement = canvasElement.querySelector(
+ '#multiple-files-mixed-state-file-input'
+ );
+ selectFiles(multipleFilesMixedStateFileInputElement, [
+ new File(['.'.repeat(25)], 'file-1.txt'),
+ new File(['.'.repeat(50)], 'file-2.txt'),
+ new File(['.'.repeat(501)], 'file-3.txt'),
+ ]);
+
+ const longFilenameFileInputElement = canvasElement.querySelector('#long-filename-file-input');
+ selectFiles(longFilenameFileInputElement, [
+ new File(
+ [''],
+ 'long-filename-lorem-ipsum-dolor-sit-amet-consectetur-adipiscing-elit-mauris-a-ante-pharetra-hendrerit-turpis-nec-volutpat-leo-duis-consectetur-tincidunt-risus-non-lobortis.txt'
+ ),
+ ]);
+}
diff --git a/.storybook/stories/file-input/advanced-file-input.stories.ts b/.storybook/stories/file-input/advanced-file-input.stories.ts
new file mode 100644
index 0000000000..9edf69b214
--- /dev/null
+++ b/.storybook/stories/file-input/advanced-file-input.stories.ts
@@ -0,0 +1,75 @@
+/*
+ * Copyright (c) 2016-2024 Broadcom. All Rights Reserved.
+ * The term "Broadcom" refers to Broadcom Inc. and/or its subsidiaries.
+ * This software is released under MIT license.
+ * The full license information can be found in LICENSE in the root directory of this project.
+ */
+
+import { FormsModule } from '@angular/forms';
+import { ClrFileInputModule, ClrFormLayout, commonStringsDefault } from '@clr/angular';
+import { moduleMetadata, StoryFn, StoryObj } from '@storybook/angular';
+
+export default {
+ title: 'File Input/Advanced File Input',
+ decorators: [
+ moduleMetadata({
+ imports: [FormsModule, ClrFileInputModule],
+ }),
+ ],
+ argTypes: {
+ // inputs
+ clrButtonLabel: { type: 'string' },
+ // form inputs
+ clrLayout: { control: false },
+ },
+ args: {
+ // inputs
+ clrButtonLabel: commonStringsDefault.browse,
+ },
+};
+
+const advancedAdvancedFileInputTemplate = `
+
+`;
+
+const advancedAdvancedFileInputStoryFn: StoryFn = args => ({
+ template: advancedAdvancedFileInputTemplate,
+ props: { ...args },
+});
+
+export const VerticalAdvancedFileInput: StoryObj = {
+ render: advancedAdvancedFileInputStoryFn,
+ args: {
+ clrLayout: ClrFormLayout.VERTICAL,
+ },
+};
+
+export const HorizontalAdvancedFileInput: StoryObj = {
+ render: advancedAdvancedFileInputStoryFn,
+ args: {
+ clrLayout: ClrFormLayout.HORIZONTAL,
+ },
+};
+
+export const CompactAdvancedFileInput: StoryObj = {
+ render: advancedAdvancedFileInputStoryFn,
+ args: {
+ clrLayout: ClrFormLayout.COMPACT,
+ },
+};
diff --git a/.storybook/stories/file-input/file-input-states.stories.ts b/.storybook/stories/file-input/file-input-states.stories.ts
index 597682217b..e13b1e0ebc 100644
--- a/.storybook/stories/file-input/file-input-states.stories.ts
+++ b/.storybook/stories/file-input/file-input-states.stories.ts
@@ -27,68 +27,10 @@ export default {
const fileInputStatesTemplate: StoryFn = args => ({
template: `
+Advanced File Input Component
+
+
+
File Input CSS-Only