diff --git a/shapenator.js b/shapenator.js
index 557589287..637c42193 100644
--- a/shapenator.js
+++ b/shapenator.js
@@ -253,10 +253,50 @@ const facings = [
 	fs.writeFileSync(_root + 'blockstates/pattern_storage.json', JSON.stringify(blockstate, null, '\t'))
 }
 
+// Drive Viewer
+{
+	const states = ['idle', 'working']
+	const machine = 'drive_viewer'
+
+	const blockstate = {
+		multipart: []
+	}
+
+	for (const face of facings) {
+		for (const state of states) {
+			blockstate.multipart.push({
+				when: {
+					facing: face.facing,
+					worker: state
+				},
+
+				apply: {
+					model: 'overdrive_that_matters:block/' + machine + '_' + state,
+					y: face.y ? face.y : undefined
+				}
+			});
+		}
+
+		blockstate.multipart.push({
+			when: {
+				facing: face.facing,
+				drive: true
+			},
+
+			apply: {
+				model: 'overdrive_that_matters:block/' + machine + '_drive_part',
+				y: face.y ? face.y : undefined
+			}
+		});
+	}
+
+	fs.writeFileSync(_root + 'blockstates/' + machine + '.json', JSON.stringify(blockstate, null, '\t'))
+}
+
 // Машины с WorkerState
 {
 	const to_generate = ['matter_scanner', 'matter_replicator', 'matter_decomposer']
-	const to_generate_semi = ['matter_bottler', 'drive_viewer']
+	const to_generate_semi = ['matter_bottler']
 	const states = ['idle', 'working', 'error']
 	const states_semi = ['idle', 'working']
 
diff --git a/src/main/java/ru/dbotthepony/mc/otm/block/BlockDriveViewer.java b/src/main/java/ru/dbotthepony/mc/otm/block/BlockDriveViewer.java
index e8fbf6596..2678c4dee 100644
--- a/src/main/java/ru/dbotthepony/mc/otm/block/BlockDriveViewer.java
+++ b/src/main/java/ru/dbotthepony/mc/otm/block/BlockDriveViewer.java
@@ -9,6 +9,7 @@ import net.minecraft.world.level.block.entity.BlockEntityTicker;
 import net.minecraft.world.level.block.entity.BlockEntityType;
 import net.minecraft.world.level.block.state.BlockState;
 import net.minecraft.world.level.block.state.StateDefinition;
+import net.minecraft.world.level.block.state.properties.BooleanProperty;
 import ru.dbotthepony.mc.otm.Registry;
 import ru.dbotthepony.mc.otm.block.entity.BlockEntityDriveViewer;
 
@@ -29,9 +30,12 @@ public class BlockDriveViewer extends BlockMatteryRotatable implements EntityBlo
 		return p_153212_.isClientSide || p_153214_ != Registry.BlockEntities.DRIVE_VIEWER ? null : BlockEntityDriveViewer::ticker;
 	}
 
+	public static final BooleanProperty DRIVE_PRESENT = BooleanProperty.create("drive");
+
 	@Override
 	protected void createBlockStateDefinition(StateDefinition.Builder<Block, BlockState> builder) {
 		super.createBlockStateDefinition(builder);
 		builder.add(SEMI_WORKER_STATE);
+		builder.add(DRIVE_PRESENT);
 	}
 }
diff --git a/src/main/java/ru/dbotthepony/mc/otm/block/entity/BlockEntityDriveViewer.java b/src/main/java/ru/dbotthepony/mc/otm/block/entity/BlockEntityDriveViewer.java
index 45fbd3c31..5309ac16c 100644
--- a/src/main/java/ru/dbotthepony/mc/otm/block/entity/BlockEntityDriveViewer.java
+++ b/src/main/java/ru/dbotthepony/mc/otm/block/entity/BlockEntityDriveViewer.java
@@ -13,6 +13,7 @@ import net.minecraft.world.level.block.entity.BlockEntity;
 import net.minecraft.world.level.block.entity.BlockEntityType;
 import net.minecraft.world.level.block.state.BlockState;
 import ru.dbotthepony.mc.otm.Registry;
+import ru.dbotthepony.mc.otm.block.BlockDriveViewer;
 import ru.dbotthepony.mc.otm.block.entity.worker.WorkerState;
 import ru.dbotthepony.mc.otm.capability.MatteryCapability;
 import ru.dbotthepony.mc.otm.capability.MatteryMachineEnergyStorage;
@@ -34,15 +35,31 @@ public class BlockEntityDriveViewer extends BlockEntityMatteryPowered {
 		super.setChanged();
 
 		if (level != null) {
+			var state = getBlockState();
+
+			if (drive_slot.getItem(0).getCapability(MatteryCapability.DRIVE).isPresent()) {
+				if (!getBlockState().getValue(BlockDriveViewer.DRIVE_PRESENT)) {
+					state = state.setValue(BlockDriveViewer.DRIVE_PRESENT, true);
+				}
+			} else {
+				if (getBlockState().getValue(BlockDriveViewer.DRIVE_PRESENT)) {
+					state = state.setValue(BlockDriveViewer.DRIVE_PRESENT, false);
+				}
+			}
+
 			if (drive_slot.getItem(0).getCapability(MatteryCapability.DRIVE).isPresent() && canIOItems()) {
 				if (getBlockState().getValue(WorkerState.SEMI_WORKER_STATE) != WorkerState.WORKING) {
-					level.setBlock(getBlockPos(), getBlockState().setValue(WorkerState.SEMI_WORKER_STATE, WorkerState.WORKING), Block.UPDATE_CLIENTS);
+					state = state.setValue(WorkerState.SEMI_WORKER_STATE, WorkerState.WORKING);
 				}
 			} else {
 				if (getBlockState().getValue(WorkerState.SEMI_WORKER_STATE) != WorkerState.IDLE) {
-					level.setBlock(getBlockPos(), getBlockState().setValue(WorkerState.SEMI_WORKER_STATE, WorkerState.IDLE), Block.UPDATE_CLIENTS);
+					state = state.setValue(WorkerState.SEMI_WORKER_STATE, WorkerState.IDLE);
 				}
 			}
+
+			if (state != getBlockState()) {
+				level.setBlock(getBlockPos(), state, Block.UPDATE_CLIENTS);
+			}
 		}
 	}